New upstream version 3.6.6
authorGert Wollny <gewo@debian.org>
Fri, 9 Apr 2021 07:46:34 +0000 (09:46 +0200)
committerGert Wollny <gewo@debian.org>
Fri, 9 Apr 2021 07:46:34 +0000 (09:46 +0200)
675 files changed:
ANNOUNCE
CHANGES
CMake/3rdparty.cmake
CMake/DCMTKConfig.cmake.in
CMake/GenerateDCMTKConfigure.cmake
CMake/dcmtkPrepare.cmake
CMake/osconfig.h.in
CMakeLists.txt
COPYRIGHT
CREDITS
INSTALL
Makefile
README
README.md
VERSION
config/aclocal.m4
config/configure
config/configure.in
config/confmod
config/docs/macros.txt
config/include/dcmtk/config/osconfig.h.in
config/modules
config/rootconf
config/tests/arith.cc
config/tests/stack.cc
dcmdata/apps/dcm2json.cc
dcmdata/apps/dcmconv.cc
dcmdata/apps/dump2dcm.cc
dcmdata/apps/img2dcm.cc
dcmdata/apps/mdfdsman.cc
dcmdata/apps/xml2dcm.cc
dcmdata/data/SC.dump
dcmdata/data/VLP.dump
dcmdata/data/dicom.dic
dcmdata/data/private.dic
dcmdata/docs/cda2dcm.man
dcmdata/docs/dcm2json.man
dcmdata/docs/dcm2xml.man
dcmdata/docs/dcmconv.man
dcmdata/docs/dcmodify.man
dcmdata/docs/dump2dcm.man
dcmdata/docs/img2dcm.man
dcmdata/docs/pdf2dcm.man
dcmdata/docs/stl2dcm.man
dcmdata/docs/xml2dcm.man
dcmdata/include/dcmtk/dcmdata/dcbytstr.h
dcmdata/include/dcmtk/dcmdata/dccodec.h
dcmdata/include/dcmtk/dcmdata/dcdatset.h
dcmdata/include/dcmtk/dcmdata/dcdeftag.h
dcmdata/include/dcmtk/dcmdata/dcelem.h
dcmdata/include/dcmtk/dcmdata/dcerror.h
dcmdata/include/dcmtk/dcmdata/dcfilefo.h
dcmdata/include/dcmtk/dcmdata/dcitem.h
dcmdata/include/dcmtk/dcmdata/dcjson.h
dcmdata/include/dcmtk/dcmdata/dcobject.h
dcmdata/include/dcmtk/dcmdata/dcpath.h
dcmdata/include/dcmtk/dcmdata/dcpixel.h
dcmdata/include/dcmtk/dcmdata/dcrleccd.h
dcmdata/include/dcmtk/dcmdata/dcrlecce.h
dcmdata/include/dcmtk/dcmdata/dcsequen.h
dcmdata/include/dcmtk/dcmdata/dcuid.h
dcmdata/include/dcmtk/dcmdata/dcvr.h
dcmdata/include/dcmtk/dcmdata/dcvrat.h
dcmdata/include/dcmtk/dcmdata/dcvrds.h
dcmdata/include/dcmtk/dcmdata/dcvrfd.h
dcmdata/include/dcmtk/dcmdata/dcvrfl.h
dcmdata/include/dcmtk/dcmdata/dcvris.h
dcmdata/include/dcmtk/dcmdata/dcvrpn.h
dcmdata/include/dcmtk/dcmdata/dcvrsv.h
dcmdata/include/dcmtk/dcmdata/dcvruv.h
dcmdata/include/dcmtk/dcmdata/libi2d/i2d.h
dcmdata/libi2d/i2djpgs.cc
dcmdata/libsrc/dcbytstr.cc
dcmdata/libsrc/dccodec.cc
dcmdata/libsrc/dcdatset.cc
dcmdata/libsrc/dcddirif.cc
dcmdata/libsrc/dcdictbi.cc
dcmdata/libsrc/dcelem.cc
dcmdata/libsrc/dcencdoc.cc
dcmdata/libsrc/dcerror.cc
dcmdata/libsrc/dcfilefo.cc
dcmdata/libsrc/dcitem.cc
dcmdata/libsrc/dcjson.cc
dcmdata/libsrc/dclist.cc
dcmdata/libsrc/dcmetinf.cc
dcmdata/libsrc/dcobject.cc
dcmdata/libsrc/dcpath.cc
dcmdata/libsrc/dcpixel.cc
dcmdata/libsrc/dcpixseq.cc
dcmdata/libsrc/dcrleccd.cc
dcmdata/libsrc/dcrlecce.cc
dcmdata/libsrc/dcsequen.cc
dcmdata/libsrc/dcswap.cc
dcmdata/libsrc/dcuid.cc
dcmdata/libsrc/dcvr.cc
dcmdata/libsrc/dcvrat.cc
dcmdata/libsrc/dcvrds.cc
dcmdata/libsrc/dcvrfd.cc
dcmdata/libsrc/dcvrfl.cc
dcmdata/libsrc/dcvris.cc
dcmdata/libsrc/dcvrobow.cc
dcmdata/libsrc/dcvrod.cc
dcmdata/libsrc/dcvrof.cc
dcmdata/libsrc/dcvrol.cc
dcmdata/libsrc/dcvrov.cc
dcmdata/libsrc/dcvrpn.cc
dcmdata/libsrc/dcvrpobw.cc
dcmdata/libsrc/dcvrsv.cc
dcmdata/libsrc/dcvruv.cc
dcmdata/tests/CMakeLists.txt
dcmdata/tests/Makefile.dep
dcmdata/tests/Makefile.in
dcmdata/tests/tdict.cc
dcmdata/tests/telemlen.cc
dcmdata/tests/tests.cc
dcmdata/tests/tfilter.cc
dcmdata/tests/tparser.cc
dcmdata/tests/tpath.cc
dcmdata/tests/tpread.cc
dcmdata/tests/tsequen.cc [new file with mode: 0644]
dcmdata/tests/tvrcomp.cc
dcmdata/tests/tvrdatim.cc
dcmdata/tests/tvrds.cc
dcmect/CMakeLists.txt [new file with mode: 0644]
dcmect/Makefile.in [new file with mode: 0644]
dcmect/configure [new file with mode: 0755]
dcmect/data/Makefile.in [new file with mode: 0644]
dcmect/docs/Makefile.in [new file with mode: 0644]
dcmect/docs/dcmect.dox [new file with mode: 0644]
dcmect/etc/Makefile.in [new file with mode: 0644]
dcmect/include/CMakeLists.txt [new file with mode: 0644]
dcmect/include/Makefile.in [new file with mode: 0644]
dcmect/include/dcmtk/dcmect/def.h [new file with mode: 0644]
dcmect/include/dcmtk/dcmect/enhanced_ct.h [new file with mode: 0644]
dcmect/include/dcmtk/dcmect/types.h [new file with mode: 0644]
dcmect/libsrc/CMakeLists.txt [new file with mode: 0644]
dcmect/libsrc/Makefile.dep [new file with mode: 0644]
dcmect/libsrc/Makefile.in [new file with mode: 0644]
dcmect/libsrc/enhanced_ct.cc [new file with mode: 0644]
dcmect/libsrc/types.cc [new file with mode: 0644]
dcmect/tests/CMakeLists.txt [new file with mode: 0644]
dcmect/tests/Makefile.dep [new file with mode: 0644]
dcmect/tests/Makefile.in [new file with mode: 0644]
dcmect/tests/t_huge_concat.cc [new file with mode: 0644]
dcmect/tests/t_roundtrip.cc [new file with mode: 0644]
dcmect/tests/tests.cc [new file with mode: 0644]
dcmfg/include/dcmtk/dcmfg/concatenationcreator.h [new file with mode: 0644]
dcmfg/include/dcmtk/dcmfg/concatenationloader.h [new file with mode: 0644]
dcmfg/include/dcmtk/dcmfg/fg.h
dcmfg/include/dcmtk/dcmfg/fgbase.h
dcmfg/include/dcmtk/dcmfg/fgctacquisitiondetails.h [new file with mode: 0644]
dcmfg/include/dcmtk/dcmfg/fgctacquisitiontype.h [new file with mode: 0644]
dcmfg/include/dcmtk/dcmfg/fgctadditionalxraysource.h [new file with mode: 0644]
dcmfg/include/dcmtk/dcmfg/fgctexposure.h [new file with mode: 0644]
dcmfg/include/dcmtk/dcmfg/fgctgeometry.h [new file with mode: 0644]
dcmfg/include/dcmtk/dcmfg/fgctimageframetype.h [new file with mode: 0644]
dcmfg/include/dcmtk/dcmfg/fgctposition.h [new file with mode: 0644]
dcmfg/include/dcmtk/dcmfg/fgctreconstruction.h [new file with mode: 0644]
dcmfg/include/dcmtk/dcmfg/fgcttabledynamics.h [new file with mode: 0644]
dcmfg/include/dcmtk/dcmfg/fgctxraydetails.h [new file with mode: 0644]
dcmfg/include/dcmtk/dcmfg/fgdefine.h
dcmfg/include/dcmtk/dcmfg/fgderimg.h
dcmfg/include/dcmtk/dcmfg/fgfact.h
dcmfg/include/dcmtk/dcmfg/fgfracon.h
dcmfg/include/dcmtk/dcmfg/fgframeanatomy.h
dcmfg/include/dcmtk/dcmfg/fgframevoilut.h
dcmfg/include/dcmtk/dcmfg/fgimagedatatype.h
dcmfg/include/dcmtk/dcmfg/fginterface.h
dcmfg/include/dcmtk/dcmfg/fgirradiationeventid.h [new file with mode: 0644]
dcmfg/include/dcmtk/dcmfg/fgparametricmapframetype.h
dcmfg/include/dcmtk/dcmfg/fgpixeltransform.h
dcmfg/include/dcmtk/dcmfg/fgpixmsr.h
dcmfg/include/dcmtk/dcmfg/fgplanor.h
dcmfg/include/dcmtk/dcmfg/fgplanorvol.h
dcmfg/include/dcmtk/dcmfg/fgplanpo.h
dcmfg/include/dcmtk/dcmfg/fgplanposvol.h
dcmfg/include/dcmtk/dcmfg/fgrealworldvaluemapping.h
dcmfg/include/dcmtk/dcmfg/fgseg.h
dcmfg/include/dcmtk/dcmfg/fgtemporalposition.h [new file with mode: 0644]
dcmfg/include/dcmtk/dcmfg/fgtypes.h
dcmfg/include/dcmtk/dcmfg/fgusimagedescription.h
dcmfg/include/dcmtk/dcmfg/stack.h
dcmfg/include/dcmtk/dcmfg/stackinterface.h
dcmfg/libsrc/CMakeLists.txt
dcmfg/libsrc/Makefile.dep
dcmfg/libsrc/Makefile.in
dcmfg/libsrc/concatenationcreator.cc [new file with mode: 0644]
dcmfg/libsrc/concatenationloader.cc [new file with mode: 0644]
dcmfg/libsrc/fg.cc
dcmfg/libsrc/fgbase.cc
dcmfg/libsrc/fgctacquisitiondetails.cc [new file with mode: 0644]
dcmfg/libsrc/fgctacquisitiontype.cc [new file with mode: 0644]
dcmfg/libsrc/fgctadditionalxraysource.cc [new file with mode: 0644]
dcmfg/libsrc/fgctexposure.cc [new file with mode: 0644]
dcmfg/libsrc/fgctgeometry.cc [new file with mode: 0644]
dcmfg/libsrc/fgctimageframetype.cc [new file with mode: 0644]
dcmfg/libsrc/fgctposition.cc [new file with mode: 0644]
dcmfg/libsrc/fgctreconstruction.cc [new file with mode: 0644]
dcmfg/libsrc/fgcttabledynamics.cc [new file with mode: 0644]
dcmfg/libsrc/fgctxraydetails.cc [new file with mode: 0644]
dcmfg/libsrc/fgderimg.cc
dcmfg/libsrc/fgfact.cc
dcmfg/libsrc/fgfracon.cc
dcmfg/libsrc/fgframeanatomy.cc
dcmfg/libsrc/fgframevoilut.cc
dcmfg/libsrc/fgimagedatatype.cc
dcmfg/libsrc/fginterface.cc
dcmfg/libsrc/fgirradiationeventid.cc [new file with mode: 0644]
dcmfg/libsrc/fgparametricmapframetype.cc
dcmfg/libsrc/fgpixeltransform.cc
dcmfg/libsrc/fgpixmsr.cc
dcmfg/libsrc/fgplanor.cc
dcmfg/libsrc/fgplanorvol.cc
dcmfg/libsrc/fgplanpo.cc
dcmfg/libsrc/fgplanposvol.cc
dcmfg/libsrc/fgrealworldvaluemapping.cc
dcmfg/libsrc/fgseg.cc
dcmfg/libsrc/fgtemporalposition.cc [new file with mode: 0644]
dcmfg/libsrc/fgtypes.cc
dcmfg/libsrc/fgusimagedescription.cc
dcmfg/libsrc/stack.cc
dcmfg/libsrc/stackinterface.cc
dcmfg/tests/CMakeLists.txt
dcmfg/tests/Makefile.dep
dcmfg/tests/Makefile.in
dcmfg/tests/t_concatenation_creator.cc [new file with mode: 0644]
dcmfg/tests/t_concatenation_loader.cc [new file with mode: 0644]
dcmfg/tests/t_ct_acquisition_details.cc [new file with mode: 0644]
dcmfg/tests/t_ct_acquisition_type.cc [new file with mode: 0644]
dcmfg/tests/t_ct_image_frame_type.cc [new file with mode: 0644]
dcmfg/tests/t_ct_position.cc [new file with mode: 0644]
dcmfg/tests/t_ct_table_dynamics.cc [new file with mode: 0644]
dcmfg/tests/t_deriv_image.cc
dcmfg/tests/t_frame_content.cc
dcmfg/tests/t_irradiation_event_identification.cc [new file with mode: 0644]
dcmfg/tests/tests.cc
dcmimage/apps/dcm2pnm.cc
dcmimage/apps/dcmquant.cc
dcmimage/apps/dcmscale.cc
dcmimage/docs/dcm2pnm.man
dcmimage/docs/dcmscale.man
dcmimage/include/dcmtk/dcmimage/diqthash.h
dcmimage/libsrc/dipitiff.cc
dcmimgle/include/dcmtk/dcmimgle/dimoopxt.h
dcmimgle/include/dcmtk/dcmimgle/diovpln.h
dcmimgle/libsrc/diimage.cc
dcmimgle/libsrc/diovlay.cc
dcmimgle/libsrc/diovpln.cc
dcmiod/include/dcmtk/dcmiod/cielabutil.h
dcmiod/include/dcmtk/dcmiod/iodcommn.h
dcmiod/include/dcmtk/dcmiod/iodcontentitemmacro.h
dcmiod/include/dcmtk/dcmiod/ioddef.h
dcmiod/include/dcmtk/dcmiod/iodimage.h
dcmiod/include/dcmtk/dcmiod/iodmacro.h
dcmiod/include/dcmtk/dcmiod/iodreferences.h
dcmiod/include/dcmtk/dcmiod/iodrules.h
dcmiod/include/dcmtk/dcmiod/iodtypes.h
dcmiod/include/dcmtk/dcmiod/iodutil.h
dcmiod/include/dcmtk/dcmiod/modacquisitioncontext.h
dcmiod/include/dcmtk/dcmiod/modbase.h
dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h
dcmiod/include/dcmtk/dcmiod/modenhequipment.h
dcmiod/include/dcmtk/dcmiod/modenhusimage.h
dcmiod/include/dcmtk/dcmiod/modenhusseries.h
dcmiod/include/dcmtk/dcmiod/modequipment.h
dcmiod/include/dcmtk/dcmiod/modfloatingpointimagepixel.h
dcmiod/include/dcmtk/dcmiod/modfor.h
dcmiod/include/dcmtk/dcmiod/modgeneralimage.h
dcmiod/include/dcmtk/dcmiod/modgeneralseries.h
dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h
dcmiod/include/dcmtk/dcmiod/modhelp.h
dcmiod/include/dcmtk/dcmiod/modimagepixel.h
dcmiod/include/dcmtk/dcmiod/modimagepixelbase.h
dcmiod/include/dcmtk/dcmiod/modimagepixelvariant.h
dcmiod/include/dcmtk/dcmiod/modmultiframedimension.h
dcmiod/include/dcmtk/dcmiod/modmultiframefg.h
dcmiod/include/dcmtk/dcmiod/modpatient.h
dcmiod/include/dcmtk/dcmiod/modpatientstudy.h
dcmiod/include/dcmtk/dcmiod/modsegmentationseries.h
dcmiod/include/dcmtk/dcmiod/modsopcommon.h
dcmiod/include/dcmtk/dcmiod/modsynchronisation.h
dcmiod/include/dcmtk/dcmiod/modusfor.h
dcmiod/libsrc/Makefile.dep
dcmiod/libsrc/cielabutil.cc
dcmiod/libsrc/iodcommn.cc
dcmiod/libsrc/iodcontentitemmacro.cc
dcmiod/libsrc/iodmacro.cc
dcmiod/libsrc/iodreferences.cc
dcmiod/libsrc/iodrules.cc
dcmiod/libsrc/iodtypes.cc
dcmiod/libsrc/iodutil.cc
dcmiod/libsrc/modacquisitioncontext.cc
dcmiod/libsrc/modbase.cc
dcmiod/libsrc/modcommoninstanceref.cc
dcmiod/libsrc/modenhequipment.cc
dcmiod/libsrc/modenhusimage.cc
dcmiod/libsrc/modenhusseries.cc
dcmiod/libsrc/modequipment.cc
dcmiod/libsrc/modfloatingpointimagepixel.cc
dcmiod/libsrc/modfor.cc
dcmiod/libsrc/modgeneralimage.cc
dcmiod/libsrc/modgeneralseries.cc
dcmiod/libsrc/modgeneralstudy.cc
dcmiod/libsrc/modhelp.cc
dcmiod/libsrc/modimagepixel.cc
dcmiod/libsrc/modimagepixelbase.cc
dcmiod/libsrc/modmultiframedimension.cc
dcmiod/libsrc/modmultiframefg.cc
dcmiod/libsrc/modpatient.cc
dcmiod/libsrc/modpatientstudy.cc
dcmiod/libsrc/modsegmentationseries.cc
dcmiod/libsrc/modsopcommon.cc
dcmiod/libsrc/modsynchronization.cc
dcmiod/libsrc/modusfor.cc
dcmiod/tests/CMakeLists.txt
dcmiod/tests/Makefile.dep
dcmiod/tests/Makefile.in
dcmiod/tests/tcielabutil.cc
dcmiod/tests/tcodes.cc [new file with mode: 0644]
dcmiod/tests/tests.cc
dcmiod/tests/timagepixel.cc
dcmjpeg/apps/dcmdjpeg.cc
dcmjpeg/docs/dcmj2pnm.man
dcmjpeg/docs/dcmjpeg.dox
dcmjpeg/include/dcmtk/dcmjpeg/djcodecd.h
dcmjpeg/include/dcmtk/dcmjpeg/djcodece.h
dcmjpeg/libsrc/djcodecd.cc
dcmjpeg/libsrc/djcodece.cc
dcmjpls/apps/CMakeLists.txt
dcmjpls/apps/Makefile.in
dcmjpls/apps/dcmcjpls.cc
dcmjpls/apps/dcmdjpls.cc
dcmjpls/docs/dcmcjpls.man
dcmjpls/docs/dcmjpls.dox
dcmjpls/docs/dcml2pnm.man
dcmjpls/include/dcmtk/dcmjpls/djcodecd.h
dcmjpls/include/dcmtk/dcmjpls/djcodece.h
dcmjpls/include/dcmtk/dcmjpls/djcparam.h
dcmjpls/libcharls/CMakeLists.txt
dcmjpls/libcharls/Makefile.in
dcmjpls/libcharls/header.cc
dcmjpls/libcharls/intrface.h
dcmjpls/libsrc/CMakeLists.txt
dcmjpls/libsrc/djcodecd.cc
dcmjpls/libsrc/djcodece.cc
dcmnet/apps/CMakeLists.txt
dcmnet/apps/Makefile.dep
dcmnet/apps/Makefile.in
dcmnet/apps/dcmrecv.cc
dcmnet/apps/findscu.cc
dcmnet/apps/movescu.cc
dcmnet/apps/storescp.cc
dcmnet/docs/dcmrecv.man
dcmnet/docs/echoscu.man
dcmnet/docs/findscu.man
dcmnet/docs/movescu.man
dcmnet/docs/storescp.man
dcmnet/docs/storescu.man
dcmnet/etc/storescp.cfg
dcmnet/etc/storescu.cfg
dcmnet/include/dcmtk/dcmnet/dfindscu.h
dcmnet/include/dcmtk/dcmnet/dimse.h
dcmnet/include/dcmtk/dcmnet/diutil.h
dcmnet/include/dcmtk/dcmnet/dul.h
dcmnet/include/dcmtk/dcmnet/scp.h
dcmnet/include/dcmtk/dcmnet/scpcfg.h
dcmnet/include/dcmtk/dcmnet/scu.h
dcmnet/libsrc/Makefile.dep
dcmnet/libsrc/assoc.cc
dcmnet/libsrc/dfindscu.cc
dcmnet/libsrc/dimdump.cc
dcmnet/libsrc/dimfind.cc
dcmnet/libsrc/dimget.cc
dcmnet/libsrc/dimmove.cc
dcmnet/libsrc/dimstore.cc
dcmnet/libsrc/dul.cc
dcmnet/libsrc/dulfsm.cc
dcmnet/libsrc/dulparse.cc
dcmnet/libsrc/scp.cc
dcmnet/libsrc/scpcfg.cc
dcmnet/libsrc/scppool.cc
dcmnet/libsrc/scu.cc
dcmnet/tests/CMakeLists.txt
dcmnet/tests/Makefile.dep
dcmnet/tests/Makefile.in
dcmnet/tests/tdimse.cc [new file with mode: 0644]
dcmnet/tests/tdump.cc
dcmnet/tests/tests.cc
dcmnet/tests/tscusession.cc [new file with mode: 0644]
dcmpmap/include/dcmtk/dcmpmap/dpmparametricmapiod.h
dcmpmap/libsrc/Makefile.dep
dcmpmap/libsrc/dpmparametricmapiod.cc
dcmpstat/apps/dcmprscu.cc
dcmpstat/apps/dcmpsprt.cc
dcmpstat/apps/dcmpsrcv.cc
dcmpstat/include/dcmtk/dcmpstat/dvpstx.h
dcmpstat/libsrc/Makefile.dep
dcmpstat/libsrc/dviface.cc
dcmpstat/libsrc/dvpscu.cc
dcmpstat/libsrc/dvsighdl.cc
dcmqrdb/docs/dcmqrscp.man
dcmqrdb/etc/dcmqrprf.cfg
dcmqrdb/include/dcmtk/dcmqrdb/dcmqrcbf.h
dcmqrdb/include/dcmtk/dcmqrdb/dcmqrcnf.h
dcmqrdb/libsrc/dcmqrcnf.cc
dcmqrdb/libsrc/dcmqrdbi.cc
dcmrt/include/dcmtk/dcmrt/drmdose.h
dcmrt/libsrc/drtrbs4.cc
dcmrt/libsrc/drtrbs8.cc
dcmseg/include/dcmtk/dcmseg/segdef.h
dcmseg/include/dcmtk/dcmseg/segdoc.h
dcmseg/include/dcmtk/dcmseg/segment.h
dcmseg/include/dcmtk/dcmseg/segtypes.h
dcmseg/include/dcmtk/dcmseg/segutils.h
dcmseg/libsrc/Makefile.dep
dcmseg/libsrc/segdoc.cc
dcmseg/libsrc/segment.cc
dcmseg/libsrc/segtypes.cc
dcmseg/libsrc/segutils.cc
dcmseg/tests/CMakeLists.txt
dcmseg/tests/Makefile.dep
dcmseg/tests/Makefile.in
dcmseg/tests/tconcat_binary.cc [new file with mode: 0644]
dcmseg/tests/tests.cc
dcmseg/tests/troundtrip.cc [new file with mode: 0644]
dcmseg/tests/tutils.cc
dcmsign/apps/Makefile.dep
dcmsign/apps/dcmsign.cc
dcmsign/docs/dcmsign.dox
dcmsign/docs/dcmsign.man
dcmsign/include/dcmtk/dcmsign/dcsighlp.h [new file with mode: 0644]
dcmsign/include/dcmtk/dcmsign/dcsignat.h
dcmsign/include/dcmtk/dcmsign/sialgo.h
dcmsign/include/dcmtk/dcmsign/siautopr.h
dcmsign/include/dcmtk/dcmsign/sibrsapr.h
dcmsign/include/dcmtk/dcmsign/sicert.h
dcmsign/include/dcmtk/dcmsign/sicertvf.h
dcmsign/include/dcmtk/dcmsign/sicreapr.h
dcmsign/include/dcmtk/dcmsign/sidsa.h
dcmsign/include/dcmtk/dcmsign/siecdsa.h [new file with mode: 0644]
dcmsign/include/dcmtk/dcmsign/siexit.h [new file with mode: 0644]
dcmsign/include/dcmtk/dcmsign/simac.h
dcmsign/include/dcmtk/dcmsign/simaccon.h
dcmsign/include/dcmtk/dcmsign/simd5.h
dcmsign/include/dcmtk/dcmsign/sinullpr.h
dcmsign/include/dcmtk/dcmsign/siprivat.h
dcmsign/include/dcmtk/dcmsign/sipurpos.h [new file with mode: 0644]
dcmsign/include/dcmtk/dcmsign/siripemd.h
dcmsign/include/dcmtk/dcmsign/sirsa.h
dcmsign/include/dcmtk/dcmsign/sisha1.h
dcmsign/include/dcmtk/dcmsign/sisprof.h
dcmsign/include/dcmtk/dcmsign/sisrpr.h [new file with mode: 0644]
dcmsign/include/dcmtk/dcmsign/sisrvpr.h [new file with mode: 0644]
dcmsign/include/dcmtk/dcmsign/sitsfs.h [new file with mode: 0644]
dcmsign/include/dcmtk/dcmsign/sitstamp.h
dcmsign/include/dcmtk/dcmsign/sitypes.h
dcmsign/libsrc/CMakeLists.txt
dcmsign/libsrc/Makefile.dep
dcmsign/libsrc/Makefile.in
dcmsign/libsrc/dcsighlp.cc [new file with mode: 0644]
dcmsign/libsrc/dcsignat.cc
dcmsign/libsrc/siautopr.cc
dcmsign/libsrc/sibrsapr.cc
dcmsign/libsrc/sicert.cc
dcmsign/libsrc/sicertvf.cc
dcmsign/libsrc/sicreapr.cc
dcmsign/libsrc/siecdsa.cc [new file with mode: 0644]
dcmsign/libsrc/simaccon.cc
dcmsign/libsrc/sinullpr.cc
dcmsign/libsrc/siprivat.cc
dcmsign/libsrc/sipurpos.cc [new file with mode: 0644]
dcmsign/libsrc/sisprof.cc
dcmsign/libsrc/sisrpr.cc [new file with mode: 0644]
dcmsign/libsrc/sisrvpr.cc [new file with mode: 0644]
dcmsign/libsrc/sitsfs.cc [new file with mode: 0644]
dcmsign/libsrc/sitstamp.cc [new file with mode: 0644]
dcmsign/libsrc/sitypes.cc
dcmsr/include/dcmtk/dcmsr/cmr/cid100.h
dcmsr/include/dcmtk/dcmsr/cmr/cid10013.h
dcmsr/include/dcmtk/dcmsr/cmr/cid10033.h
dcmsr/include/dcmtk/dcmsr/cmr/cid11.h
dcmsr/include/dcmtk/dcmsr/cmr/cid244.h
dcmsr/include/dcmtk/dcmsr/cmr/cid29.h
dcmsr/include/dcmtk/dcmsr/cmr/cid4020.h
dcmsr/include/dcmtk/dcmsr/cmr/cid4021.h
dcmsr/include/dcmtk/dcmsr/cmr/cid4031.h
dcmsr/include/dcmtk/dcmsr/cmr/cid42.h
dcmsr/include/dcmtk/dcmsr/cmr/cid6147.h
dcmsr/include/dcmtk/dcmsr/cmr/cid7021.h
dcmsr/include/dcmtk/dcmsr/cmr/cid7181.h
dcmsr/include/dcmtk/dcmsr/cmr/cid7445.h
dcmsr/include/dcmtk/dcmsr/cmr/cid7452.h
dcmsr/include/dcmtk/dcmsr/cmr/cid7453.h
dcmsr/include/dcmtk/dcmsr/cmr/cid7464.h
dcmsr/include/dcmtk/dcmsr/cmr/cid7469.h
dcmsr/include/dcmtk/dcmsr/codes/dcm.h
dcmsr/include/dcmtk/dcmsr/codes/ncit.h
dcmsr/include/dcmtk/dcmsr/codes/umls.h
dcmsr/include/dcmtk/dcmsr/dsrdoc.h
dcmsr/include/dcmtk/dcmsr/dsrimgvl.h
dcmsr/include/dcmtk/dcmsr/dsrrsdcc.h [new file with mode: 0644]
dcmsr/include/dcmtk/dcmsr/dsrtypes.h
dcmsr/include/dcmtk/dcmsr/dsrwavvl.h
dcmsr/include/dcmtk/dcmsr/dsrxmld.h
dcmsr/libcmr/cid100.cc
dcmsr/libcmr/cid10013.cc
dcmsr/libcmr/cid10033.cc
dcmsr/libcmr/cid11.cc
dcmsr/libcmr/cid244.cc
dcmsr/libcmr/cid29.cc
dcmsr/libcmr/cid4020.cc
dcmsr/libcmr/cid4021.cc
dcmsr/libcmr/cid4031.cc
dcmsr/libcmr/cid4031e.cc
dcmsr/libcmr/cid42.cc
dcmsr/libcmr/cid6147.cc
dcmsr/libcmr/cid7021.cc
dcmsr/libcmr/cid7181.cc
dcmsr/libcmr/cid7445.cc
dcmsr/libcmr/cid7452.cc
dcmsr/libcmr/cid7453.cc
dcmsr/libcmr/cid7464.cc
dcmsr/libcmr/cid7469.cc
dcmsr/libsrc/CMakeLists.txt
dcmsr/libsrc/Makefile.in
dcmsr/libsrc/dsrcodvl.cc
dcmsr/libsrc/dsrdoc.cc
dcmsr/libsrc/dsrimgvl.cc
dcmsr/libsrc/dsrpficc.cc
dcmsr/libsrc/dsrplicc.cc
dcmsr/libsrc/dsrrsdcc.cc [new file with mode: 0644]
dcmsr/libsrc/dsrtypes.cc
dcmsr/libsrc/dsrwavvl.cc
dcmsr/tests/tsrcmr.cc
dcmsr/tests/tsrcodvl.cc
dcmtls/CMakeLists.txt
dcmtls/docs/certstor.txt
dcmtls/docs/dcmtls.dox
dcmtls/libsrc/Makefile.dep
dcmtls/libsrc/tlsopt.cc
dcmtls/libsrc/tlsscu.cc
dcmtls/tests/CMakeLists.txt [new file with mode: 0644]
dcmtls/tests/tests.cc [new file with mode: 0644]
dcmtls/tests/tscuscptls.cc [new file with mode: 0644]
dcmtract/include/dcmtk/dcmtract/trcmeasurement.h
dcmtract/include/dcmtk/dcmtract/trcmodtractresults.h
dcmtract/include/dcmtk/dcmtract/trcstatistic.h
dcmtract/include/dcmtk/dcmtract/trctrack.h
dcmtract/include/dcmtk/dcmtract/trctrackset.h
dcmtract/libsrc/Makefile.dep
dcmtract/libsrc/trctrack.cc
dcmwlm/apps/wlcefs.cc
dcmwlm/docs/wlmscpfs.man
dcmwlm/libsrc/wldsfs.cc
dcmwlm/libsrc/wlfsim.cc
dcmwlm/libsrc/wlmactmg.cc
docs/ANNOUNCE.365 [new file with mode: 0644]
docs/CHANGES.320
docs/CHANGES.342
docs/CHANGES.350
docs/CHANGES.352
docs/CHANGES.360
docs/CHANGES.362
docs/CHANGES.363
docs/CHANGES.366 [new file with mode: 0644]
doxygen/Makefile.in
doxygen/htmldocs.dox
doxygen/manpages/man1/cda2dcm.1
doxygen/manpages/man1/dcm2json.1
doxygen/manpages/man1/dcm2pdf.1
doxygen/manpages/man1/dcm2pnm.1
doxygen/manpages/man1/dcm2xml.1
doxygen/manpages/man1/dcmcjpeg.1
doxygen/manpages/man1/dcmcjpls.1
doxygen/manpages/man1/dcmconv.1
doxygen/manpages/man1/dcmcrle.1
doxygen/manpages/man1/dcmdjpeg.1
doxygen/manpages/man1/dcmdjpls.1
doxygen/manpages/man1/dcmdrle.1
doxygen/manpages/man1/dcmdspfn.1
doxygen/manpages/man1/dcmdump.1
doxygen/manpages/man1/dcmftest.1
doxygen/manpages/man1/dcmgpdir.1
doxygen/manpages/man1/dcmicmp.1
doxygen/manpages/man1/dcmj2pnm.1
doxygen/manpages/man1/dcml2pnm.1
doxygen/manpages/man1/dcmmkcrv.1
doxygen/manpages/man1/dcmmkdir.1
doxygen/manpages/man1/dcmmklut.1
doxygen/manpages/man1/dcmodify.1
doxygen/manpages/man1/dcmp2pgm.1
doxygen/manpages/man1/dcmprscp.1
doxygen/manpages/man1/dcmprscu.1
doxygen/manpages/man1/dcmpschk.1
doxygen/manpages/man1/dcmpsmk.1
doxygen/manpages/man1/dcmpsprt.1
doxygen/manpages/man1/dcmpsrcv.1
doxygen/manpages/man1/dcmpssnd.1
doxygen/manpages/man1/dcmqridx.1
doxygen/manpages/man1/dcmqrscp.1
doxygen/manpages/man1/dcmqrti.1
doxygen/manpages/man1/dcmquant.1
doxygen/manpages/man1/dcmrecv.1
doxygen/manpages/man1/dcmscale.1
doxygen/manpages/man1/dcmsend.1
doxygen/manpages/man1/dcmsign.1
doxygen/manpages/man1/dcod2lum.1
doxygen/manpages/man1/dconvlum.1
doxygen/manpages/man1/drtdump.1
doxygen/manpages/man1/dsr2html.1
doxygen/manpages/man1/dsr2xml.1
doxygen/manpages/man1/dsrdump.1
doxygen/manpages/man1/dump2dcm.1
doxygen/manpages/man1/echoscu.1
doxygen/manpages/man1/findscu.1
doxygen/manpages/man1/getscu.1
doxygen/manpages/man1/img2dcm.1
doxygen/manpages/man1/movescu.1
doxygen/manpages/man1/pdf2dcm.1
doxygen/manpages/man1/stl2dcm.1
doxygen/manpages/man1/storescp.1
doxygen/manpages/man1/storescu.1
doxygen/manpages/man1/termscu.1
doxygen/manpages/man1/wlmscpfs.1
doxygen/manpages/man1/xml2dcm.1
doxygen/manpages/man1/xml2dsr.1
oflog/include/dcmtk/oflog/clogger.h
oflog/include/dcmtk/oflog/config.h
oflog/include/dcmtk/oflog/configrt.h
oflog/include/dcmtk/oflog/fstreams.h
oflog/include/dcmtk/oflog/helpers/property.h
oflog/include/dcmtk/oflog/helpers/queue.h
oflog/include/dcmtk/oflog/socketap.h
oflog/include/dcmtk/oflog/streams.h
oflog/include/dcmtk/oflog/tchar.h
oflog/include/dcmtk/oflog/thread/impl/tls.h
oflog/include/dcmtk/oflog/tstring.h
oflog/libsrc/config.cc
oflog/libsrc/env.cc
oflog/libsrc/fileap.cc
oflog/libsrc/fileinfo.cc
oflog/libsrc/filter.cc
oflog/libsrc/globinit.cc
oflog/libsrc/log4judp.cc
oflog/libsrc/ntelogap.cc
oflog/libsrc/property.cc
oflog/libsrc/snprintf.cc
oflog/libsrc/sockbuff.cc
oflog/libsrc/socketap.cc
oflog/libsrc/strhelp.cc
oflog/libsrc/timehelp.cc
oflog/libsrc/winconap.cc
oflog/libsrc/windebap.cc
oflog/libsrc/winsock.cc
ofstd/include/dcmtk/ofstd/ofdatime.h
ofstd/include/dcmtk/ofstd/ofexit.h
ofstd/include/dcmtk/ofstd/offile.h
ofstd/include/dcmtk/ofstd/oflimits.h
ofstd/include/dcmtk/ofstd/ofmap.h
ofstd/include/dcmtk/ofstd/oftest.h
ofstd/include/dcmtk/ofstd/oftime.h
ofstd/include/dcmtk/ofstd/oftraits.h
ofstd/include/dcmtk/ofstd/oftypes.h
ofstd/include/dcmtk/ofstd/ofxml.h
ofstd/libsrc/Makefile.dep
ofstd/libsrc/offile.cc
ofstd/libsrc/ofstd.cc
ofstd/libsrc/ofstring.cc
ofstd/libsrc/oftempf.cc
ofstd/libsrc/oftime.cc
ofstd/tests/tatof.cc
ofstd/tests/tests.cc
ofstd/tests/tmap.cc
ofstd/tests/tofdatim.cc
ofstd/tests/txml.cc

index f4d40abdd3cd5cf22b51a7a524dd0b7d2fd1a460..9a4534be3379c47e2440b1941fa9ae2634b2af19 100644 (file)
--- a/ANNOUNCE
+++ b/ANNOUNCE
@@ -1,16 +1,14 @@
 ANNOUNCEMENT
 
-Version 3.6.5 of the OFFIS DCMTK (DICOM ToolKit) software is now available for
-public release.  This is a minor release that includes the following changes
-over the previous version 3.6.4:
+Version 3.6.6 of the OFFIS DCMTK (DICOM ToolKit) software is now available for
+public release.  This release includes the following main changes over the
+previous version 3.6.5:
 
-- DCMTK 3.6.5 builds correctly on older and up-to-date versions of GNU gcc
-  (4.4.7 to 9.2.0), Clang (3.4.2 to 9.0.0), AppleClang (11.0.0), Microsoft
-  Visual Studio (2008 to 2019), SunPro CC (5.14 and 5.15) and IBM XL C/C++
-  (16.1.1.3).
+- DCMTK 3.6.6 builds correctly on older and up-to-date versions of GNU gcc
+  (4.2.1 to 10.2.0) Clang (3.4.2 to 11.0.0), Apple Clang 11.0.0,
+  Microsoft Visual Studio (2008 to 2019) and SunPro CC (5.14 and 5.15).
 
 - Tested with the following operating systems/environments:
-
   - Android on arm64
   - Cygwin on x86_64
   - FreeBSD on x86_64
@@ -20,134 +18,94 @@ over the previous version 3.6.4:
   - OpenBSD on x86_64
   - OpenIndiana on x86
   - Solaris on x86
-  - Windows (and MinGW) on x86_64 and x86
+  - Windows (including MinGW and Cygwin) on x86_64 and x86
 
   For a complete list of tested systems and compilers, see the INSTALL file.
 
-- GNU Autoconf is still deprecated, running 'configure' emits a warning by
-  default.  Support for GNU Autoconf will be removed after this release.
-
-- Updated data dictionary, SOP Class, Frame of Reference and Transfer Syntax
-  UIDs for the recently approved changes to the DICOM standard (i.e. Supplements
-  and CPs), up to DICOM standard release DICOM 2019c plus Supplement 175 (Second
-  Generation Radiotherapy - C-Arm RT Treatment Modalities).
-
-- Added support for directory record "RADIOTHERAPY" that has been introduced
-  with Supplement 147 (Second Generation Radiotherapy - Prescription and Segment
-  Annotation).
-
-- Added support for the three new 64-bit integer VRs introduced with CP-1819:
-  Other 64-bit Very Long (OV), Signed 64-bit Very Long (SV) and Unsigned 64-bit
-  Very Long (UV).
-
-- Implemented support for the Extended BCP 195 TLS Profile, introduced with
-  Supplement 206, in the dcmtls module and the various TLS-enabled DCMTK tools.
-
-- Added option to "storescu" to rename files after processing them by appending
-  ".bad" or ".good" at the end of the filename.
-
-- Added new options to "wlmscpfs" that allow for dumping incoming C-FIND
-  requests to text files using a configurable directory and filename.
-
-- Updated automatically generated Context Group classes in "dcmsr"
-  (Structured Reporting) based on DICOM 2019c.  Also updated the Code
-  definitions from the supported coding schemes such as DICOM, NCIt and UMLS.
-
-- Further enhanced DICOM Structured Reporting (SR) module "dcmsr":
-
-  - Added support for the Performed Imaging Agent Administration SR IOD and the
-    Planned Imaging Agent Administration SR IOD introduced with Supplement 164.
+- Updated data dictionary, SOP classes, well-known frame of references,
+  transfer syntaxes, code definitions and supported context group classes for
+  DICOM standard release 2020e.
 
-  - Added support for the Synchronization Module, which is required for some SR
-    IODs, e.g. Procedure Log SR or Performed Imaging Agent Administration SR.
+- Added new DCMTK module dcmect, which facilitates creation, loading, (partly)
+  modification and storing Enhanced CT objects:
 
-  - Added initial support for coding scheme "SCT" (SNOMED CT) by defining those
-    CODE_SCT_xxx code constants that are needed for the "cmr" submodule.
+  - Also included is a general Concatenation API that allows for creating and
+    re-assembling Concatenations from given DICOM datasets. Right now, only
+    uncompressed ("unencapsulated") pixel data is supported.
 
-  - Updated SR Template classes from DCMR for the 2019b edition of the DICOM
-    standard, i.e. all SRT (SNOMED RT) codes were replaced by their associated
-    SCT (SNOMED CT) counterparts. This change was introduced with CP-1850.
+  - The existing Segmentation API (dcmseg) as well as the new Enhanced CT API
+    (dcmect) both support writing and reading Concatenations via dedicated
+    methods.
 
-  - Added new print flag PF_printEmptyCodes, which prints the text "empty code"
-    for empty codes instead of "invalid code". This new flag is e.g. used for
-    the output stream operator of the DSRCodedEntryValue class.
+  - Thanks to GE Aviation for sponsoring this feature.
 
-- The list of elliptic curves to be negotiated as part of a TLS is now created
-  dynamically, i.e. it is tested at runtime which elliptic curves are supported
-  by the installed OpenSSL library.
+- Major revision of JSON export tool (dcm2json), which should now be fully
+  standard compliant.
 
-- Allow disabling Functional Group checks when writing Segmentations and
-  Parametric Map objects in order to speed up writing objects with many frames.
+- Major revision of the dcmsign module, which now supports Elliptic Curve
+  (ECDSA) signatures, the DICOM SR RSA Digital Signature Profile, and CRLs in
+  hashed certificate directories.  During signature verification the chain of
+  trust for the signer certificates are now fully checked and there is limited
+  support for the creation and verification of trusted timestamps.
 
-- Added macro that enables the wide char (wchar_t*) support of the XML parser
-  that is part of the DCMTK (ofstd/ofxml). This support is limited to Windows
-  systems and still regarded as experimental (see documentation for details).
+- Added support for the Rendition Selection Document IOD, which has been
+  introduced with Supplement 202 (Real-Time Video), to the dcmsr module.
 
-- The tool "findscu" now always returns with a non-zero exit code when an error
-  occurred, e.g. when association negotiation failed.
+- Added support for the new Waveform Storage SOP Classes that have been
+  introduced with Supplement 217 (Neurophysiology Waveforms) to the DICOMDIR
+  generation code and to the dcmsr module.
 
-- CMake-related enhancements:
+- Added support for the new 2nd generation RT Storage SOP Classes that have
+  been introduced with Supplement 175, 176 and 199, as well as for the new
+  Encapsulated OBJ and MTL Storage SOP Classes (Supplement 208) to the
+  DICOMDIR generation code.
 
-  - DCMTK now understands and makes use of the CMake variable CMAKE_CXX_STANDARD
-    when a CMake version that supports it is employed (CMake 3.1.3 and newer).
+- Added TLS support to the DcmSCP and DcmSCPPool classes and to the dcmrecv
+  command line tool.
 
-  - Added CMake option that controls whether DCMTK gets compiled using the
-    multi-threaded static or DLL runtime library when using MSVC on Windows.
+- Updated and completely revised DIMSE Status Code definitions.  Now, the
+  definitions and also the log output are consistent with the current edition
+  of the DICOM standard.
 
-- Various fixes and extensions to the JPEG-LS implementation:
+- Significant performance enhancements for code that gets an item from or
+  inserts an item into a sequence with a large number of items.
 
-  - Added command line options controlling how odd-length bitstreams are
-    padded to even length (for compatibility with HP LOCO).
+- DCMTK now successfully compiles when UNICODE/_UNICODE is defined on Windows.
 
-  - Added command line option that causes the decoder to store images even
-    though an error occurred during the decoding process, which may be helpful
-    for slightly truncated bitstreams.
+- When compiling on Windows, new CMake options can now be used to control the
+  Win32 build model (multi-threaded or multi-threaded DLL).
 
-  - Enable setting of individual JPEG-LS encoding parameters
-    T1, T2, T3 and RESET.
-
-  - Various bugfixes in JPEG-LS encoder and decoder.
-
-- Fixed binary Segmentation object creation when width is not dividable by 8.
-
-- Fixed wrong DIMSE status codes A8xx (for C-STORE and C-FIND) and A800 (for
-  C-GET and C-MOVE), which were never defined in the official DICOM standard.
-  Now, the DCMTK uses the correct DIMSE status code 0122H for "SOP Class not
-  supported" for all DIMSE messages.
-
-- Fixed various issues that occurred after the official 3.6.4 release.
+- Fixed various issues that occurred after the official 3.6.5 release.
   See CHANGES file for details.
 
-
 Many people have contributed to this new release of DCMTK, appearing here in
 alphabetical order.  Thank you very much for your support!
 
-  Victor Derks <vderks@delftdi.com>
-  Chinna Durai <chinnadurai410@gmail.com>
-  Holger Franke <franke@image-instruments.de>
-  Sergei Gordey <serg.gordey@gmail.com>
-  Daniel Grieger <Daniel.Grieger@ith-icoserve.com>
-  Bengt Gustafsson <Bengt.Gustafsson@contextvision.se>
-  Alexander Haderer <alexander.haderer@loescap.de>
+  Michel Amat (GitHub user "amatm")
+  Bartosz Bialoskorski <bartoszbialoskorski@gmail.com>
+  Jesper Bojesen <jbojesen@vitalimages.com>
+  Marcel Claus <Marcel.Claus@med.uni-jena.de>
+  Jake Cobb <Jake.Cobb@varian.com>
+  Martin Czarnowski <czarnowski@examion.com>
+  Matthias Gierlings <matthias.gierlings@ruhr-uni-bochum.de>
+  Niklas Johansson (GitHub user "Raphexion")
+  Andreas Keizers <an-kei@web.de>
   Peter Klotz <Peter.Klotz@ith-icoserve.com>
-  Brian Lucas <brian.lucas@heartit.com>
-  Mathieu Malaterre <mathieu.malaterre@gmail.com>
-  Hans Meine <hans.meine@mevis.fraunhofer.de>
+  Damien Lerat
+  Mathieu Malaterre <malat@debian.org>
+  Robert Mulcahey <rob@asteris.com>
+  Maria Nedyak <mashanedyak@gmail.com>
+  Steve Pieper <pieper@isomics.com>
+  Sergey Razuvaev <Sergey.Razuvaev@waveaccess.ru>
+  Markus Sabin <Markus.Sabin@soft-gate.de>
   Maria Samoylova <mashanedyak@gmail.com>
-  Martin Wenger <Martin.Wenger@klinikum-hef.de>
-  Brian Wise <brian.wise@medtronic.com>
-  Grischa Zengel <ggz@zmt.info>
+  Adrian Schmidt-Foehre <A.Schmidt-Foehre@mint-medical.de>
+  Waldo Valenzuela <waldo.valenzuela@artorg.unibe.ch>
 
-  Andreas Gravgaard Andersen (GitHub user "agravgaard")
-  Hans Johnson (GitHub user "hjmjohnson")
-  Stefano Magni
+  DCMTK forum users "CStarkey", "JustSomeGuy", "Shaeto", and "ruben.cruz"
+  GitHub user "iboB"
 
-  Forum user "AlexanderLysenko"
-  GitHub user "eborisch"
-  GitHub user "FreddyFunk"
-
-Members of the DCMTK Team who have worked on this release are
-(in alphabetical order):
+Members of the DCMTK Team who have worked on this release are:
 
   Pedro Arizpe Gomez <arizpegomez@offis.de>
   Marco Eichelberg <eichelberg@offis.de>
@@ -155,15 +113,8 @@ Members of the DCMTK Team who have worked on this release are
   Joerg Riesmeier <dicom@jriesmeier.com>
   Jan Schlamelcher <schlamelcher@offis.de>
 
-Student associates:
-
-  Nikolas Goldhammer <nikolasgoldhammer@gmail.com>
-
-Also see CREDITS file for projects and companies who have been generously
-supporting DCMTK.
-
 The DCMTK software can be downloaded via:
 
   https://dicom.offis.de/dcmtk or https://www.dcmtk.org/
 
-OFFIS e.V., Oldenburg, Germany, 2019-10-28
+OFFIS e.V., Oldenburg, Germany, 2021-01-14
diff --git a/CHANGES b/CHANGES
index b7fc06550c6edab18e47868a7a5452b653472fd1..488e84388ecd0fe36f0323a7496aadfcb3dd498e 100644 (file)
--- a/CHANGES
+++ b/CHANGES
@@ -1,12 +1,13 @@
 
 In earlier versions of DCMTK, changes between releases had been documented in a
-CHANGES.XXX file inside DCMTK's main directory.
+CHANGES.XXX file inside DCMTK's main directory, with "XXX" referring to the
+version number of the release.
 
-Now, the CHANGES.XXX file has been moved to the dcmtk/doc folder with the latest
-one being updated every time that a new DCMTK version is released.  Thus it
-always contains all DCMTK changes between the last DCMTK release and the most
-recent one.
+Now, the CHANGES.XXX file has been moved to the dcmtk/docs folder (in the
+source code package) with the latest one being updated every time a new DCMTK
+version is released.  Thus, it always contains all DCMTK changes between the
+previous DCMTK release and the most recent one.
 
 For very recent changes, i. e. those changes to DCMTK that have been applied
-after the most recent release, see the DCMTK git repository log at
-http://git.dcmtk.org/ .
+after the most recent release, see the commit history of DCMTK's git repository
+at https://git.dcmtk.org/.
index 4a388aaf29aaa5fd55a39480c2ec179b35a222cc..43aa282efe25c315656b4d037226c7f9dadc8e8f 100644 (file)
-if(WIN32 AND NOT MINGW)
-
+set(USE_FIND_PACKAGE_DOCS "Control whether libraries are searched via CMake's find_package() mechanism or a Windows specific fallback")
+if(WIN32)
   # For Windows, we don't used FIND_PACKAGE because DCMTK usually is used with its
   # own set of 3rd-party support libraries that can be downloaded from DCMTK's
   # website (pre-built).
-
-  # libxml support: find out whether user has library
-  file(GLOB LIBXML_DIR "${DCMTK_SOURCE_DIR}/../libxml2*")
-  find_path(WITH_LIBXMLINC "/include/libxml/parser.h" "${LIBXML_DIR}" NO_DEFAULT_PATH)
-
-  # libpng support: find out whether user has library
-  file(GLOB LIBPNG_DIR "${DCMTK_SOURCE_DIR}/../libpng*")
-  find_path(WITH_LIBPNGINC "include/png.h" "${LIBPNG_DIR}" NO_DEFAULT_PATH)
-
-  # libtiff support: find out whether user has library
-  file(GLOB LIBTIFF_DIR "${DCMTK_SOURCE_DIR}/../libtiff*")
-  find_path(WITH_LIBTIFFINC "include/tiff.h" "${LIBTIFF_DIR}" NO_DEFAULT_PATH)
-
-  # OpenSSL support: find out whether user has library
-  file(GLOB OPENSSL_DIR "${DCMTK_SOURCE_DIR}/../openssl*")
-  find_path(WITH_OPENSSLINC "include/openssl/ssl.h" "${OPENSSL_DIR}" NO_DEFAULT_PATH)
-
-  # zlib support: find out whether user has library
-  file(GLOB ZLIB_DIR "${DCMTK_SOURCE_DIR}/../zlib*")
-  find_path(WITH_ZLIBINC "include/zlib.h" "${ZLIB_DIR}" NO_DEFAULT_PATH)
-
-  # sndfile support: find out whether user has library. Needed for module dcmwave (not in public DCMTK yet, marked as advanced)
-  file(GLOB SNDFILE_DIR "${DCMTK_SOURCE_DIR}/../libsndfile*")
-  find_path(WITH_SNDFILEINC "sndfile.h" "${SNDFILE_DIR}" NO_DEFAULT_PATH)
-  mark_as_advanced(SNDFILE_DIR WITH_SNDFILEINC)
-
-  # libiconv support: find out whether user has library
-  file(GLOB LIBICONV_DIR "${DCMTK_SOURCE_DIR}/../libiconv*")
-  find_path(WITH_LIBICONVINC "include/iconv.h" "${LIBICONV_DIR}" NO_DEFAULT_PATH)
-
-  # OpenJPEG support: find out whether user has library
-  file(GLOB OPENJPEG_DIR "${DCMTK_SOURCE_DIR}/../openjpeg*")
-  find_path(WITH_OPENJPEGINC "lib/openjp2_o.lib" "${OPENJPEG_DIR}" NO_DEFAULT_PATH)
-
-  # libxml support: configure compiler
-  if(DCMTK_WITH_XML)
-    if(WITH_LIBXMLINC)
-      set(LIBXML_INCDIR "${WITH_LIBXMLINC}/include")
-      set(LIBXML_LIBDIR "${WITH_LIBXMLINC}/lib")
-      set(LIBXML_LIBS debug "${LIBXML_LIBDIR}/libxml2_d.lib" optimized "${LIBXML_LIBDIR}/libxml2_o.lib" debug "${LIBXML_LIBDIR}/iconv_d.lib" optimized "${LIBXML_LIBDIR}/iconv_o.lib")
-      message(STATUS "Info: DCMTK XML support will be enabled")
-      set(WITH_LIBXML 1)
-      # this hides some warnings that are emitted when linking against libxmlXXX.lib instead of linking the DLL directly
-      add_definitions("-DLIBXML_STATIC")
-    else() # turn off library if library path not set
-      message(STATUS "Warning: XML support will be disabled because libxml2 directory is not specified. Correct path and re-enable DCMTK_WITH_XML.")
-      set(DCMTK_WITH_XML OFF CACHE BOOL "" FORCE)
-      set(WITH_LIBXML "")
-    endif()
-  endif()
-
-  # libpng support: configure compiler
-  if(DCMTK_WITH_PNG)
-    if(WITH_LIBPNGINC)
-      set(LIBPNG_INCDIR "${WITH_LIBPNGINC}/include")
-      set(LIBPNG_LIBDIR "${WITH_LIBPNGINC}/lib")
-      set(LIBPNG_LIBS debug "${LIBPNG_LIBDIR}/libpng_d.lib" optimized "${LIBPNG_LIBDIR}/libpng_o.lib")
-      message(STATUS "Info: DCMTK PNG support will be enabled")
-      set(WITH_LIBPNG 1)
-    else() # turn off library if library path not set
-      message(STATUS "Warning: PNG support will be disabled because libpng directory was not specified. Correct path and re-enable DCMTK_WITH_PNG.")
-      set(DCMTK_WITH_PNG OFF CACHE BOOL "" FORCE)
-      set(WITH_LIBPNG "")
-    endif()
-  endif()
-
-  # libtiff support: configure compiler
-  if(DCMTK_WITH_TIFF)
-    if(WITH_LIBTIFFINC)
-      set(LIBTIFF_INCDIR "${WITH_LIBTIFFINC}/include")
-      set(LIBTIFF_LIBDIR "${WITH_LIBTIFFINC}/lib")
-      set(LIBTIFF_LIBS debug "${LIBTIFF_LIBDIR}/libtiff_d.lib" optimized "${LIBTIFF_LIBDIR}/libtiff_o.lib")
-      message(STATUS "Info: DCMTK TIFF support will be enabled")
-      set(WITH_LIBTIFF 1)
-    else() # turn off library if library path not set
-      message(STATUS "Warning: TIFF support will be disabled because libtiff directory was not specified. Correct path and re-enable DCMTK_WITH_TIFF.")
-      set(DCMTK_WITH_TIFF OFF CACHE BOOL "" FORCE)
-      set(WITH_LIBTIFF "")
-    endif()
-  endif()
-
-  # OpenSSL support: configure compiler
-  if(DCMTK_WITH_OPENSSL)
-    if(WITH_OPENSSLINC)
-      include(CheckCXXSourceCompiles)
-      set(OPENSSL_BINDIR "${WITH_OPENSSLINC}/bin")
-      set(OPENSSL_INCDIR "${WITH_OPENSSLINC}/include")
-      set(OPENSSL_LIBDIR "${WITH_OPENSSLINC}/lib")
-      # starting with OpenSSL 1.1.0, the Windows crypt32 library is needed for a static link of OpenSSL.
-      set(OPENSSL_LIBS "crypt32" debug "${OPENSSL_LIBDIR}/dcmtkssl_d.lib" optimized "${OPENSSL_LIBDIR}/dcmtkssl_o.lib" debug "${OPENSSL_LIBDIR}/dcmtkcrypto_d.lib" optimized "${OPENSSL_LIBDIR}/dcmtkcrypto_o.lib")
-      set(TEMP_INCLUDES "${CMAKE_REQUIRED_INCLUDES}")
-      list(APPEND CMAKE_REQUIRED_INCLUDES "${OPENSSL_INCDIR}")
-      CHECK_CXX_SOURCE_COMPILES("extern \"C\" {\n#include <openssl/ssl.h>\n}\nint main(){\n#if OPENSSL_VERSION_NUMBER < 0x10001000L\n#error OpenSSL too old\n#endif\n}\n" OPENSSL_VERSION_CHECK)
-      set(CMAKE_REQUIRED_INCLUDES "${TEMP_INCLUDES}")
-      if(OPENSSL_VERSION_CHECK)
-        message(STATUS "Info: DCMTK OPENSSL support will be enabled")
-        set(WITH_OPENSSL 1)
-      else()
-        message(STATUS "Info: DCMTK OPENSSL support will be disabled: DCMTK requires OpenSSL version 1.0.1 or newer")
-        set(DCMTK_WITH_OPENSSL OFF CACHE BOOL "" FORCE)
-        set(WITH_OPENSSL "")
-      endif()
-    else() # turn off library if library path not set
-      message(STATUS "Warning: OPENSSL support will be disabled because openssl directory was not specified. Correct path and re-enable DCMTK_WITH_OPENSSL.")
-      set(DCMTK_WITH_OPENSSL OFF CACHE BOOL "" FORCE)
-      set(WITH_OPENSSL "")
-    endif()
-  endif()
-
-  # zlib support: configure compiler
-  if(DCMTK_WITH_ZLIB)
-    if(WITH_ZLIBINC)
-      set(ZLIB_INCDIR "${WITH_ZLIBINC}/include")
-      set(ZLIB_LIBDIR "${WITH_ZLIBINC}/lib")
-      set(ZLIB_LIBS debug "${ZLIB_LIBDIR}/zlib_d.lib" optimized "${ZLIB_LIBDIR}/zlib_o.lib")
-      message(STATUS "Info: DCMTK ZLIB support will be enabled")
-      set(WITH_ZLIB 1)
-    else() # turn off library if library path not set
-      message(STATUS "Warning: ZLIB support will be disabled because zlib directory was not specified. Correct path and re-enable DCMTK_WITH_ZLIB.")
-      set(DCMTK_WITH_ZLIB OFF CACHE BOOL "" FORCE)
-      set(WITH_ZLIB "")
-    endif()
-  endif()
-
-  # sndfile support: configure compiler
-  if(DCMTK_WITH_SNDFILE)
-    if(WITH_SNDFILEINC)
-      set(SNDFILE_INCDIR "${WITH_SNDFILEINC}/include")
-      set(SNDFILE_LIBDIR "${WITH_SNDFILEINC}/lib")
-      set(SNDFILE_LIBS debug "${SNDFILE_LIBDIR}/libsndfile_d.lib" optimized "${SNDFILE_LIBDIR}/libsndfile_o.lib")
-      message(STATUS "Info: DCMTK SNDFILE support will be enabled")
-      set(WITH_SNDFILE 1)
-    else() # turn off library if library path not set
-      message(STATUS "Warning: SNDFILE support will be disabled because libsndfile directory was not specified. Correct path and re-enable DCMTK_WITH_SNDFILE.")
-      set(DCMTK_WITH_SNDFILE OFF CACHE BOOL "" FORCE)
-      set(WITH_SNDFILE "")
-    endif()
-  endif()
-
-  # libiconv support: configure compiler
-  if(DCMTK_WITH_ICONV)
-    if(WITH_LIBICONVINC)
-      set(LIBICONV_INCDIR "${WITH_LIBICONVINC}/include")
-      set(LIBICONV_LIBDIR "${WITH_LIBICONVINC}/lib")
-      set(LIBICONV_LIBS debug "${LIBICONV_LIBDIR}/libiconv_d.lib" optimized "${LIBICONV_LIBDIR}/libiconv_o.lib")
-      message(STATUS "Info: DCMTK ICONV support will be enabled")
-      set(WITH_LIBICONV 1)
-    else() # turn off library if library path not set
-      message(STATUS "Warning: ICONV support will be disabled because libiconv directory was not specified. Correct path and re-enable DCMTK_WITH_ICONV.")
-      set(DCMTK_WITH_ICONV OFF CACHE BOOL "" FORCE)
-      set(WITH_LIBICONV "")
-    endif()
+  if(MINGW)
+    set(DCMTK_USE_FIND_PACKAGE TRUE CACHE BOOL "${USE_FIND_PACKAGE_DOCS}")
+  else()
+    set(DCMTK_USE_FIND_PACKAGE FALSE CACHE BOOL "${USE_FIND_PACKAGE_DOCS}")
   endif()
-
-  # OpenJPEG support: configure compiler
-  if(DCMTK_WITH_OPENJPEG)
-    if(WITH_OPENJPEGINC)
-      # Unfortunately, OpenJPEG uses a version number in the include path. This needs special handling.
-      file(GLOB OPENJPEG2_DIR "${WITH_OPENJPEGINC}/include/openjpeg*")
-      find_path(WITH_OPENJPEGINC1 "openjpeg.h" "${OPENJPEG2_DIR}" NO_DEFAULT_PATH)
-      if ("${WITH_OPENJPEGINC1}" STREQUAL "WITH_OPENJPEGINC1-NOTFOUND")
-          message(STATUS "Info: DCMTK OpenJPEG support will be disabled because the header files were not found.")
-          set(DCMTK_WITH_OPENJPEG OFF CACHE BOOL "" FORCE)
-          set(WITH_OPENJPEG "")
-      else()
-          set(OPENJPEG_INCDIR "${WITH_OPENJPEGINC1}")
-          set(OPENJPEG_LIBDIR "${WITH_OPENJPEGINC}/lib")
-          set(OPENJPEG_LIBS debug "${OPENJPEG_LIBDIR}/openjp2_d.lib" optimized "${OPENJPEG_LIBDIR}/openjp2_o.lib")
-          message(STATUS "Info: DCMTK OpenJPEG support will be enabled")
-          set(WITH_OPENJPEG 1)
-      endif()
-    else() # turn off library if library path not set
-      message(STATUS "Warning: OpenJPEG support will be disabled because openjpeg directory was not specified. Correct path and re-enable DCMTK_WITH_OPENJPEG.")
-      set(DCMTK_WITH_OPENJPEG OFF CACHE BOOL "" FORCE)
-      set(WITH_OPENJPEG "")
-    endif()
+else()
+  # Only find_package is supported
+  set(DCMTK_USE_FIND_PACKAGE TRUE CACHE BOOL "${USE_FIND_PACKAGE_DOCS}")
+  if(NOT DCMTK_USE_FIND_PACKAGE)
+    message(WARNING "Only find_package is supported on this platform, overriding user setting of DCMTK_USE_FIND_PACKAGE.")
+    set(DCMTK_USE_FIND_PACKAGE TRUE FORCE)
   endif()
+endif()
+mark_as_advanced(DCMTK_USE_FIND_PACKAGE)
 
-else(WIN32 AND NOT MINGW)
-
+if(DCMTK_USE_FIND_PACKAGE)
   # Find TIFF
   if(DCMTK_WITH_TIFF)
     find_package(TIFF QUIET)
@@ -356,8 +192,189 @@ else(WIN32 AND NOT MINGW)
       set(OPENJPEG_LIBS ${OPENJPEG_LIBRARIES})
     endif()
   endif()
+else()
+  if(NOT DEFINED DCMTK_SUPPORT_LIBRARIES_DIR)
+    get_filename_component(DCMTK_SUPPORT_LIBRARIES_DIR "${DCMTK_SOURCE_DIR}" PATH)
+    set(DCMTK_SUPPORT_LIBRARIES_DIR "${DCMTK_SUPPORT_LIBRARIES_DIR}" CACHE PATH "The directory to search for precompiled DCMTK support libraries.")
+  endif()
+
+  # libxml support: find out whether user has library
+  file(GLOB LIBXML_DIR "${DCMTK_SUPPORT_LIBRARIES_DIR}/libxml2*")
+  find_path(WITH_LIBXMLINC "${DCMTK_SUPPORT_LIBRARIES_DIR}/include/libxml/parser.h" "${LIBXML_DIR}" NO_DEFAULT_PATH)
+
+  # libpng support: find out whether user has library
+  file(GLOB LIBPNG_DIR "${DCMTK_SUPPORT_LIBRARIES_DIR}/libpng*")
+  find_path(WITH_LIBPNGINC "include/png.h" "${LIBPNG_DIR}" NO_DEFAULT_PATH)
+
+  # libtiff support: find out whether user has library
+  file(GLOB LIBTIFF_DIR "${DCMTK_SUPPORT_LIBRARIES_DIR}/libtiff*")
+  find_path(WITH_LIBTIFFINC "include/tiff.h" "${LIBTIFF_DIR}" NO_DEFAULT_PATH)
+
+  # OpenSSL support: find out whether user has library
+  file(GLOB OPENSSL_DIR "${DCMTK_SUPPORT_LIBRARIES_DIR}/openssl*")
+  find_path(WITH_OPENSSLINC "include/openssl/ssl.h" "${OPENSSL_DIR}" NO_DEFAULT_PATH)
+
+  # zlib support: find out whether user has library
+  file(GLOB ZLIB_DIR "${DCMTK_SUPPORT_LIBRARIES_DIR}/zlib*")
+  find_path(WITH_ZLIBINC "include/zlib.h" "${ZLIB_DIR}" NO_DEFAULT_PATH)
+
+  # sndfile support: find out whether user has library. Needed for module dcmwave (not in public DCMTK yet, marked as advanced)
+  file(GLOB SNDFILE_DIR "${DCMTK_SUPPORT_LIBRARIES_DIR}/libsndfile*")
+  find_path(WITH_SNDFILEINC "sndfile.h" "${SNDFILE_DIR}" NO_DEFAULT_PATH)
+  mark_as_advanced(SNDFILE_DIR WITH_SNDFILEINC)
+
+  # libiconv support: find out whether user has library
+  file(GLOB LIBICONV_DIR "${DCMTK_SUPPORT_LIBRARIES_DIR}/libiconv*")
+  find_path(WITH_LIBICONVINC "include/iconv.h" "${LIBICONV_DIR}" NO_DEFAULT_PATH)
 
-endif(WIN32 AND NOT MINGW)
+  # OpenJPEG support: find out whether user has library
+  file(GLOB OPENJPEG_DIR "${DCMTK_SUPPORT_LIBRARIES_DIR}/openjpeg*")
+  find_path(WITH_OPENJPEGINC "lib/openjp2_o.lib" "${OPENJPEG_DIR}" NO_DEFAULT_PATH)
+
+  # libxml support: configure compiler
+  if(DCMTK_WITH_XML)
+    if(WITH_LIBXMLINC)
+      set(LIBXML_INCDIR "${WITH_LIBXMLINC}/include")
+      set(LIBXML_LIBDIR "${WITH_LIBXMLINC}/lib")
+      set(LIBXML_LIBS debug "${LIBXML_LIBDIR}/libxml2_d.lib" optimized "${LIBXML_LIBDIR}/libxml2_o.lib" debug "${LIBXML_LIBDIR}/iconv_d.lib" optimized "${LIBXML_LIBDIR}/iconv_o.lib")
+      message(STATUS "Info: DCMTK XML support will be enabled")
+      set(WITH_LIBXML 1)
+      # this hides some warnings that are emitted when linking against libxmlXXX.lib instead of linking the DLL directly
+      add_definitions("-DLIBXML_STATIC")
+    else() # turn off library if library path not set
+      message(STATUS "Warning: XML support will be disabled because libxml2 directory is not specified. Correct path and re-enable DCMTK_WITH_XML.")
+      set(DCMTK_WITH_XML OFF CACHE BOOL "" FORCE)
+      set(WITH_LIBXML "")
+    endif()
+  endif()
+
+  # libpng support: configure compiler
+  if(DCMTK_WITH_PNG)
+    if(WITH_LIBPNGINC)
+      set(LIBPNG_INCDIR "${WITH_LIBPNGINC}/include")
+      set(LIBPNG_LIBDIR "${WITH_LIBPNGINC}/lib")
+      set(LIBPNG_LIBS debug "${LIBPNG_LIBDIR}/libpng_d.lib" optimized "${LIBPNG_LIBDIR}/libpng_o.lib")
+      message(STATUS "Info: DCMTK PNG support will be enabled")
+      set(WITH_LIBPNG 1)
+    else() # turn off library if library path not set
+      message(STATUS "Warning: PNG support will be disabled because libpng directory was not specified. Correct path and re-enable DCMTK_WITH_PNG.")
+      set(DCMTK_WITH_PNG OFF CACHE BOOL "" FORCE)
+      set(WITH_LIBPNG "")
+    endif()
+  endif()
+
+  # libtiff support: configure compiler
+  if(DCMTK_WITH_TIFF)
+    if(WITH_LIBTIFFINC)
+      set(LIBTIFF_INCDIR "${WITH_LIBTIFFINC}/include")
+      set(LIBTIFF_LIBDIR "${WITH_LIBTIFFINC}/lib")
+      set(LIBTIFF_LIBS debug "${LIBTIFF_LIBDIR}/libtiff_d.lib" optimized "${LIBTIFF_LIBDIR}/libtiff_o.lib")
+      message(STATUS "Info: DCMTK TIFF support will be enabled")
+      set(WITH_LIBTIFF 1)
+    else() # turn off library if library path not set
+      message(STATUS "Warning: TIFF support will be disabled because libtiff directory was not specified. Correct path and re-enable DCMTK_WITH_TIFF.")
+      set(DCMTK_WITH_TIFF OFF CACHE BOOL "" FORCE)
+      set(WITH_LIBTIFF "")
+    endif()
+  endif()
+
+  # OpenSSL support: configure compiler
+  if(DCMTK_WITH_OPENSSL)
+    if(WITH_OPENSSLINC)
+      include(CheckCXXSourceCompiles)
+      set(OPENSSL_BINDIR "${WITH_OPENSSLINC}/bin")
+      set(OPENSSL_INCDIR "${WITH_OPENSSLINC}/include")
+      set(OPENSSL_LIBDIR "${WITH_OPENSSLINC}/lib")
+      # starting with OpenSSL 1.1.0, the Windows crypt32 library is needed for a static link of OpenSSL.
+      set(OPENSSL_LIBS "crypt32" debug "${OPENSSL_LIBDIR}/dcmtkssl_d.lib" optimized "${OPENSSL_LIBDIR}/dcmtkssl_o.lib" debug "${OPENSSL_LIBDIR}/dcmtkcrypto_d.lib" optimized "${OPENSSL_LIBDIR}/dcmtkcrypto_o.lib")
+      set(TEMP_INCLUDES "${CMAKE_REQUIRED_INCLUDES}")
+      list(APPEND CMAKE_REQUIRED_INCLUDES "${OPENSSL_INCDIR}")
+      CHECK_CXX_SOURCE_COMPILES("extern \"C\" {\n#include <openssl/ssl.h>\n}\nint main(){\n#if OPENSSL_VERSION_NUMBER < 0x10001000L\n#error OpenSSL too old\n#endif\n}\n" OPENSSL_VERSION_CHECK)
+      set(CMAKE_REQUIRED_INCLUDES "${TEMP_INCLUDES}")
+      if(OPENSSL_VERSION_CHECK)
+        message(STATUS "Info: DCMTK OPENSSL support will be enabled")
+        set(WITH_OPENSSL 1)
+      else()
+        message(STATUS "Info: DCMTK OPENSSL support will be disabled: DCMTK requires OpenSSL version 1.0.1 or newer")
+        set(DCMTK_WITH_OPENSSL OFF CACHE BOOL "" FORCE)
+        set(WITH_OPENSSL "")
+      endif()
+    else() # turn off library if library path not set
+      message(STATUS "Warning: OPENSSL support will be disabled because openssl directory was not specified. Correct path and re-enable DCMTK_WITH_OPENSSL.")
+      set(DCMTK_WITH_OPENSSL OFF CACHE BOOL "" FORCE)
+      set(WITH_OPENSSL "")
+    endif()
+  endif()
+
+  # zlib support: configure compiler
+  if(DCMTK_WITH_ZLIB)
+    if(WITH_ZLIBINC)
+      set(ZLIB_INCDIR "${WITH_ZLIBINC}/include")
+      set(ZLIB_LIBDIR "${WITH_ZLIBINC}/lib")
+      set(ZLIB_LIBS debug "${ZLIB_LIBDIR}/zlib_d.lib" optimized "${ZLIB_LIBDIR}/zlib_o.lib")
+      message(STATUS "Info: DCMTK ZLIB support will be enabled")
+      set(WITH_ZLIB 1)
+    else() # turn off library if library path not set
+      message(STATUS "Warning: ZLIB support will be disabled because zlib directory was not specified. Correct path and re-enable DCMTK_WITH_ZLIB.")
+      set(DCMTK_WITH_ZLIB OFF CACHE BOOL "" FORCE)
+      set(WITH_ZLIB "")
+    endif()
+  endif()
+
+  # sndfile support: configure compiler
+  if(DCMTK_WITH_SNDFILE)
+    if(WITH_SNDFILEINC)
+      set(SNDFILE_INCDIR "${WITH_SNDFILEINC}/include")
+      set(SNDFILE_LIBDIR "${WITH_SNDFILEINC}/lib")
+      set(SNDFILE_LIBS debug "${SNDFILE_LIBDIR}/libsndfile_d.lib" optimized "${SNDFILE_LIBDIR}/libsndfile_o.lib")
+      message(STATUS "Info: DCMTK SNDFILE support will be enabled")
+      set(WITH_SNDFILE 1)
+    else() # turn off library if library path not set
+      message(STATUS "Warning: SNDFILE support will be disabled because libsndfile directory was not specified. Correct path and re-enable DCMTK_WITH_SNDFILE.")
+      set(DCMTK_WITH_SNDFILE OFF CACHE BOOL "" FORCE)
+      set(WITH_SNDFILE "")
+    endif()
+  endif()
+
+  # libiconv support: configure compiler
+  if(DCMTK_WITH_ICONV)
+    if(WITH_LIBICONVINC)
+      set(LIBICONV_INCDIR "${WITH_LIBICONVINC}/include")
+      set(LIBICONV_LIBDIR "${WITH_LIBICONVINC}/lib")
+      set(LIBICONV_LIBS debug "${LIBICONV_LIBDIR}/libiconv_d.lib" optimized "${LIBICONV_LIBDIR}/libiconv_o.lib")
+      message(STATUS "Info: DCMTK ICONV support will be enabled")
+      set(WITH_LIBICONV 1)
+    else() # turn off library if library path not set
+      message(STATUS "Warning: ICONV support will be disabled because libiconv directory was not specified. Correct path and re-enable DCMTK_WITH_ICONV.")
+      set(DCMTK_WITH_ICONV OFF CACHE BOOL "" FORCE)
+      set(WITH_LIBICONV "")
+    endif()
+  endif()
+
+  # OpenJPEG support: configure compiler
+  if(DCMTK_WITH_OPENJPEG)
+    if(WITH_OPENJPEGINC)
+      # Unfortunately, OpenJPEG uses a version number in the include path. This needs special handling.
+      file(GLOB OPENJPEG2_DIR "${WITH_OPENJPEGINC}/include/openjpeg*")
+      find_path(WITH_OPENJPEGINC1 "openjpeg.h" "${OPENJPEG2_DIR}" NO_DEFAULT_PATH)
+      if ("${WITH_OPENJPEGINC1}" STREQUAL "WITH_OPENJPEGINC1-NOTFOUND")
+          message(STATUS "Info: DCMTK OpenJPEG support will be disabled because the header files were not found.")
+          set(DCMTK_WITH_OPENJPEG OFF CACHE BOOL "" FORCE)
+          set(WITH_OPENJPEG "")
+      else()
+          set(OPENJPEG_INCDIR "${WITH_OPENJPEGINC1}")
+          set(OPENJPEG_LIBDIR "${WITH_OPENJPEGINC}/lib")
+          set(OPENJPEG_LIBS debug "${OPENJPEG_LIBDIR}/openjp2_d.lib" optimized "${OPENJPEG_LIBDIR}/openjp2_o.lib")
+          message(STATUS "Info: DCMTK OpenJPEG support will be enabled")
+          set(WITH_OPENJPEG 1)
+      endif()
+    else() # turn off library if library path not set
+      message(STATUS "Warning: OpenJPEG support will be disabled because openjpeg directory was not specified. Correct path and re-enable DCMTK_WITH_OPENJPEG.")
+      set(DCMTK_WITH_OPENJPEG OFF CACHE BOOL "" FORCE)
+      set(WITH_OPENJPEG "")
+    endif()
+  endif()
+endif()
 
 if(NOT DEFINED DCMTK_WITH_STDLIBC_ICONV)
   include(CheckCXXSourceCompiles)
index c344bf28a3d00ca680613c1274a821a5b3c04fe3..4190503698fd2d2819605afd32ec3712d45c3d3b 100644 (file)
@@ -36,17 +36,67 @@ set(DCMTK_ENABLE_PRIVATE_TAGS @DCMTK_ENABLE_PRIVATE_TAGS@)
 set(DCMTK_ENABLE_CXX11 @DCMTK_ENABLE_CXX11@)
 set(DCMTK_CXX11_FLAGS @DCMTK_CXX11_FLAGS@)
 set(DCMTK_ENABLE_STL @DCMTK_ENABLE_STL@)
+set(DCMTK_ENABLE_STL_ALGORITHM @DCMTK_ENABLE_STL_ALGORITHM@)
+set(DCMTK_ENABLE_STL_LIMITS @DCMTK_ENABLE_STL_LIMITS@)
+set(DCMTK_ENABLE_STL_LIST @DCMTK_ENABLE_STL_LIST@)
+set(DCMTK_ENABLE_STL_MAP @DCMTK_ENABLE_STL_MAP@)
+set(DCMTK_ENABLE_STL_MEMORY @DCMTK_ENABLE_STL_MEMORY@)
+set(DCMTK_ENABLE_STL_STACK @DCMTK_ENABLE_STL_STACK@)
+set(DCMTK_ENABLE_STL_STRING @DCMTK_ENABLE_STL_STRING@)
+set(DCMTK_ENABLE_STL_SYSTEM_ERROR @DCMTK_ENABLE_STL_SYSTEM_ERROR@)
+set(DCMTK_ENABLE_STL_TUPLE @DCMTK_ENABLE_STL_TUPLE@)
+set(DCMTK_ENABLE_STL_TYPE_TRAITS @DCMTK_ENABLE_STL_TYPE_TRAITS@)
+set(DCMTK_ENABLE_STL_VECTOR @DCMTK_ENABLE_STL_VECTOR@)
 
-# DCMTK shared libraries
+set(DCMTK_FORCE_FPIC_ON_UNIX @DCMTK_FORCE_FPIC_ON_UNIX@)
+
+# DCMTK documentation
+set(DCMTK_GENERATE_DOXYGEN_TAGFILE @DCMTK_GENERATE_DOXYGEN_TAGFILE@)
+
+# DCMTK shared libraries and build model
+set(DCMTK_OVERWRITE_WIN32_COMPILER_FLAGS @DCMTK_OVERWRITE_WIN32_COMPILER_FLAGS@)
+set(DCMTK_COMPILE_WIN32_MULTITHREADED_DLL @DCMTK_COMPILE_WIN32_MULTITHREADED_DLL@)
 set(DCMTK_SHARED_LIBRARIES @BUILD_SHARED_LIBS@)
 set(DCMTK_SINGLE_SHARED_LIBRARY @BUILD_SINGLE_SHARED_LIBRARY@)
 
 # DCMTK additional options
+set(DCMTK_BUILD_APPS @BUILD_APPS@)
 set(DCMTK_WITH_THREADS @DCMTK_WITH_THREADS@)
-set(DCMTK_OVERWRITE_WIN32_COMPILER_FLAGS @DCMTK_OVERWRITE_WIN32_COMPILER_FLAGS@)
 set(DCMTK_WIDE_CHAR_FILE_IO_FUNCTIONS @DCMTK_WIDE_CHAR_FILE_IO_FUNCTIONS@)
 set(DCMTK_WIDE_CHAR_MAIN_FUNCTION @DCMTK_WIDE_CHAR_MAIN_FUNCTION@)
 set(DCMTK_ENABLE_LFS @DCMTK_ENABLE_LFS@)
+set(DCMTK_ENABLE_CHARSET_CONVERSION @DCMTK_ENABLE_CHARSET_CONVERSION@)
+
+
+# CMake builtins
+set(DCMTK_CMAKE_BUILD_TYPE @CMAKE_BUILD_TYPE@)
+set(DCMTK_CMAKE_CXX_COMPILER "@CMAKE_CXX_COMPILER@")
+
+set(DCMTK_CMAKE_CXX_FLAGS @CMAKE_CXX_FLAGS@)
+set(DCMTK_CMAKE_CXX_FLAGS_DEBUG @CMAKE_CXX_FLAGS_DEBUG@)
+set(DCMTK_CMAKE_CXX_FLAGS_RELEASE @CMAKE_CXX_FLAGS_RELEASE@)
+set(DCMTK_CMAKE_CXX_FLAGS_MINSIZEREL @CMAKE_CXX_FLAGS_MINSIZEREL@)
+set(DCMTK_CMAKE_CXX_FLAGS_RELWITHDEBINFO @CMAKE_CXX_FLAGS_RELWITHDEBINFO@)
+
+set(DCMTK_CMAKE_C_FLAGS_DEBUG @CMAKE_C_FLAGS_DEBUG@)
+set(DCMTK_CMAKE_C_FLAGS_RELEASE @CMAKE_C_FLAGS_RELEASE@)
+set(DCMTK_CMAKE_C_FLAGS_MINSIZEREL @CMAKE_C_FLAGS_MINSIZEREL@)
+set(DCMTK_CMAKE_C_FLAGS_RELWITHDEBINFO @CMAKE_C_FLAGS_RELWITHDEBINFO@)
+
+set(DCMTK_CMAKE_EXE_LINKER_FLAGS @CMAKE_EXE_LINKER_FLAGS_DEBUG@)
+set(DCMTK_CMAKE_EXE_LINKER_FLAGS_DEBUG @CMAKE_EXE_LINKER_FLAGS_DEBUG@)
+set(DCMTK_CMAKE_EXE_LINKER_FLAGS_RELEASE @CMAKE_EXE_LINKER_FLAGS_RELEASE@)
+set(DCMTK_CMAKE_EXE_LINKER_FLAGS_MINSIZEREL @CMAKE_EXE_LINKER_FLAGS_MINSIZEREL@)
+set(DCMTK_CMAKE_EXE_LINKER_FLAGS_RELWITHDEBINFO @CMAKE_EXE_LINKER_FLAGS_RELWITHDEBINFO@)
+
+set(DCMTK_CMAKE_INSTALL_BINDIR @CMAKE_INSTALL_BINDIR@)
+set(DCMTK_CMAKE_INSTALL_SYSCONFDIR @CMAKE_INSTALL_SYSCONFDIR@)
+set(DCMTK_CMAKE_INSTALL_INCLUDEDIR @CMAKE_INSTALL_INCLUDEDIR@)
+set(DCMTK_CMAKE_INSTALL_LIBDIR @CMAKE_INSTALL_LIBDIR@)
+set(DCMTK_CMAKE_INSTALL_DATAROOTDIR @CMAKE_INSTALL_DATAROOTDIR@)
+
+set(DCMTK_CMAKE_INSTALL_PREFIX "@CMAKE_INSTALL_PREFIX@")
+
 
 SET_AND_CHECK(DCMTK_TARGETS "@PACKAGE_DCMTK_CMKDIR_CONFIG@/DCMTKTargets.cmake")
 
index b067355eb219b05f0be0432a0c0122c51b4b965f..5f2ef72bcb5aa243c095aa43aaf4091286a11473 100644 (file)
@@ -777,17 +777,6 @@ if(NOT DEFINED C_CHAR_UNSIGNED)
   endif()
 endif()
 
-DCMTK_TRY_COMPILE(HAVE_CXX_BOOL "C++ type bool exists"
-    "// Minimal test for existence of 'bool' type.
-void TestBool(bool) {}
-
-int main()
-{
-  TestBool(false);
-  TestBool(true);
-  return 0;
-}")
-
 # Check for thread type
 if(HAVE_WINDOWS_H)
   set(HAVE_INT_TYPE_PTHREAD_T 1)
index 514803a419df2451336c37b6ba0935f0838d156b..23a9278cb3a55b213432b1d891a4499a13ae1134 100644 (file)
@@ -8,8 +8,8 @@ endif()
 set(DCMTK_CONFIGURATION_DONE true)
 
 # Latest CMake version tested
-if(CMAKE_BACKWARDS_COMPATIBILITY GREATER 3.15.3)
-  set(CMAKE_BACKWARDS_COMPATIBILITY 3.15.3 CACHE STRING "Latest version of CMake when this project was released." FORCE)
+if(CMAKE_BACKWARDS_COMPATIBILITY GREATER 3.18.4)
+  set(CMAKE_BACKWARDS_COMPATIBILITY 3.18.4 CACHE STRING "Latest version of CMake when this project was released." FORCE)
 endif()
 
 # CMAKE_BUILD_TYPE is set to value "Release" if none is specified by the
@@ -38,14 +38,14 @@ endif()
 #  a development snapshot and an even number indicates an official release.)
 set(DCMTK_MAJOR_VERSION 3)
 set(DCMTK_MINOR_VERSION 6)
-set(DCMTK_BUILD_VERSION 5)
+set(DCMTK_BUILD_VERSION 6)
 # The ABI is not guaranteed to be stable between different snapshots/releases,
 # so this particular version number is increased for each snapshot or release.
-set(DCMTK_ABI_VERSION 15)
+set(DCMTK_ABI_VERSION 16)
 
 # Package "release" settings (some are currently unused and, therefore, disabled)
 set(DCMTK_PACKAGE_NAME "dcmtk")
-set(DCMTK_PACKAGE_DATE "2019-10-28")
+set(DCMTK_PACKAGE_DATE "2021-01-14")
 set(DCMTK_PACKAGE_VERSION "${DCMTK_MAJOR_VERSION}.${DCMTK_MINOR_VERSION}.${DCMTK_BUILD_VERSION}")
 set(DCMTK_PACKAGE_VERSION_NUMBER ${DCMTK_MAJOR_VERSION}${DCMTK_MINOR_VERSION}${DCMTK_BUILD_VERSION})
 set(DCMTK_PACKAGE_VERSION_SUFFIX "")
@@ -263,54 +263,17 @@ set(CMAKE_RUNTIME_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/bin")
 # set project wide flags for compiler and linker
 
 if(WIN32)
-  option(DCMTK_OVERWRITE_WIN32_COMPILER_FLAGS  "Overwrite compiler flags with DCMTK's WIN32 package default values." ON)
+  option(DCMTK_OVERWRITE_WIN32_COMPILER_FLAGS  "Modify the default compiler flags selected by CMake." ON)
   option(DCMTK_COMPILE_WIN32_MULTITHREADED_DLL "Compile DCMTK using the Multithreaded DLL runtime library." OFF)
   if (BUILD_SHARED_LIBS)
     set(DCMTK_COMPILE_WIN32_MULTITHREADED_DLL ON)
   endif()
 else()
+  # these settings play no role on other platforms
   set(DCMTK_OVERWRITE_WIN32_COMPILER_FLAGS OFF)
   set(DCMTK_COMPILE_WIN32_MULTITHREADED_DLL OFF)
 endif()
 
-if(DCMTK_OVERWRITE_WIN32_COMPILER_FLAGS AND NOT BUILD_SHARED_LIBS)
-
-  # settings for Microsoft Visual Studio
-  if(CMAKE_GENERATOR MATCHES "Visual Studio .*")
-    # get Visual Studio Version
-    string(REGEX REPLACE "Visual Studio ([0-9]+).*" "\\1" VS_VERSION "${CMAKE_GENERATOR}")
-    # these settings never change even for C or C++
-    set(CMAKE_C_FLAGS_DEBUG "/MTd /Z7 /Od")
-    set(CMAKE_C_FLAGS_RELEASE "/DNDEBUG /MT /O2")
-    set(CMAKE_C_FLAGS_MINSIZEREL "/DNDEBUG /MT /O2")
-    set(CMAKE_C_FLAGS_RELWITHDEBINFO "/DNDEBUG /MTd /Z7 /Od")
-    set(CMAKE_CXX_FLAGS_DEBUG "/MTd /Z7 /Od")
-    set(CMAKE_CXX_FLAGS_RELEASE "/DNDEBUG /MT /O2")
-    set(CMAKE_CXX_FLAGS_MINSIZEREL "/DNDEBUG /MT /O2")
-    set(CMAKE_CXX_FLAGS_RELWITHDEBINFO "/DNDEBUG /MTd /Z7 /Od")
-    # specific settings for the various Visual Studio versions
-    if(VS_VERSION EQUAL 6)
-      set(CMAKE_C_FLAGS "/nologo /W3 /GX /Gy /YX")
-      set(CMAKE_CXX_FLAGS "/nologo /W3 /GX /Gy /YX /Zm500") # /Zm500 increments heap size which is needed on some system to compile templates in dcmimgle
-    endif()
-    if(VS_VERSION EQUAL 7)
-      set(CMAKE_C_FLAGS "/nologo /W3 /Gy")
-      set(CMAKE_CXX_FLAGS "/nologo /W3 /Gy")
-    endif()
-    if(VS_VERSION GREATER 7)
-      set(CMAKE_C_FLAGS "/nologo /W3 /Gy /EHsc")
-      set(CMAKE_CXX_FLAGS "/nologo /W3 /Gy /EHsc")
-    endif()
-  endif()
-
-  # settings for Borland C++
-  if(CMAKE_GENERATOR MATCHES "Borland Makefiles")
-    # further settings required? not tested for a very long time!
-    set(CMAKE_STANDARD_LIBRARIES "import32.lib cw32mt.lib")
-  endif()
-
-endif()
-
 if(WIN32 AND CMAKE_GENERATOR MATCHES "Visual Studio .*")
   # Evaluate the DCMTK_COMPILE_WIN32_MULTITHREADED_DLL option and adjust
   # the runtime library setting (/MT or /MD) accordingly
@@ -327,18 +290,20 @@ if(WIN32 AND CMAKE_GENERATOR MATCHES "Visual Studio .*")
         CMAKE_C_FLAGS_RELWITHDEBINFO
         )
 
-  if(DCMTK_COMPILE_WIN32_MULTITHREADED_DLL OR BUILD_SHARED_LIBS)
-    # Convert any /MT or /MTd option to /MD or /MDd
-    foreach(CompilerFlag ${CompilerFlags})
-        string(REPLACE "/MT" "/MD" ${CompilerFlag} "${${CompilerFlag}}")
-        set(${CompilerFlag} "${${CompilerFlag}}" CACHE STRING "msvc compiler flags" FORCE)
-    endforeach()
-  else()
-    # Convert any /MD or /MDd option to /MT or /MTd
-    foreach(CompilerFlag ${CompilerFlags})
-        string(REPLACE "/MD" "/MT" ${CompilerFlag} "${${CompilerFlag}}")
-        set(${CompilerFlag} "${${CompilerFlag}}" CACHE STRING "msvc compiler flags" FORCE)
-    endforeach()
+  if(DCMTK_OVERWRITE_WIN32_COMPILER_FLAGS OR BUILD_SHARED_LIBS)
+    if(DCMTK_COMPILE_WIN32_MULTITHREADED_DLL OR BUILD_SHARED_LIBS)
+      # Convert any /MT or /MTd option to /MD or /MDd
+      foreach(CompilerFlag ${CompilerFlags})
+          string(REPLACE "/MT" "/MD" ${CompilerFlag} "${${CompilerFlag}}")
+          set(${CompilerFlag} "${${CompilerFlag}}" CACHE STRING "msvc compiler flags" FORCE)
+      endforeach()
+    else()
+      # Convert any /MD or /MDd option to /MT or /MTd
+      foreach(CompilerFlag ${CompilerFlags})
+          string(REPLACE "/MD" "/MT" ${CompilerFlag} "${${CompilerFlag}}")
+          set(${CompilerFlag} "${${CompilerFlag}}" CACHE STRING "msvc compiler flags" FORCE)
+      endforeach()
+    endif()
   endif()
 endif()
 
index 3918adc161c7fba231321b10dbfcc21c7c475ffb..c3cf55c598eccad89bcebbe144c74d4c351e7888 100644 (file)
 /* Define to 1 if you have the `cuserid' function. */
 #cmakedefine HAVE_CUSERID @HAVE_CUSERID@
 
-/* Define if bool is a built-in type */
-#cmakedefine HAVE_CXX_BOOL @HAVE_CXX_BOOL@
-
 /* Define if volatile is a known keyword */
 #define HAVE_CXX_VOLATILE 1
 
index a042e7a5c1a156c0803ac5d0a2cb06f0b8afda59..028e1d17181870fd682b7084ea2e268419ffa456 100644 (file)
@@ -18,24 +18,18 @@ cmake_policy(VERSION "${DCMTK_CMAKE_POLICY_VERSION}")
 # Declare project
 project(DCMTK)
 
-# Check the build system
-include(CMake/dcmtkPrepare.cmake NO_POLICY_SCOPE)
-
 #-----------------------------------------------------------------------------
 # General project settings to configure DCMTK build process
 #-----------------------------------------------------------------------------
 
 # Modules to be built
-
 set(DCMTK_MODULES ofstd oflog dcmdata dcmimgle
   dcmimage dcmjpeg dcmjpls dcmtls dcmnet dcmsr
-  dcmsign dcmwlm dcmqrdb dcmpstat dcmrt dcmiod dcmfg dcmseg dcmtract dcmpmap
+  dcmsign dcmwlm dcmqrdb dcmpstat dcmrt dcmiod dcmfg
+  dcmseg dcmtract dcmpmap dcmect
   CACHE STRING "List of modules that should be built.")
 
-#-----------------------------------------------------------------------------
 # Include directories
-#-----------------------------------------------------------------------------
-
 set(DCMTK_INCLUDE_DIR "${DCMTK_BINARY_DIR}/config/include")
 foreach(inc ${DCMTK_MODULES})
   list(APPEND DCMTK_INCLUDE_DIR "${DCMTK_SOURCE_DIR}/${inc}/include")
@@ -43,11 +37,17 @@ endforeach()
 
 include_directories(${DCMTK_INCLUDE_DIR})
 
+#-----------------------------------------------------------------------------
+# Check the build system
+#-----------------------------------------------------------------------------
+
+include(CMake/dcmtkPrepare.cmake NO_POLICY_SCOPE)
+
 #-----------------------------------------------------------------------------
 # Prepare osconfig.h
 #-----------------------------------------------------------------------------
 
-# add the osconfig.h.in file
+# Add the osconfig.h.in file
 configure_file("${DCMTK_SOURCE_DIR}/CMake/osconfig.h.in"
                "${DCMTK_BINARY_DIR}/config/include/dcmtk/config/osconfig.h")
 
@@ -100,7 +100,7 @@ install(FILES "${DCMTK_BINARY_DIR}/config/include/dcmtk/config/osconfig.h"
         COMPONENT include)
 
 # Install DCMTK's general documentation files
-install(FILES ANNOUNCE CHANGES COPYRIGHT CREDITS FAQ HISTORY VERSION
+install(FILES ANNOUNCE COPYRIGHT CREDITS FAQ HISTORY VERSION
         DESTINATION "${CMAKE_INSTALL_DOCDIR}"
         COMPONENT doc)
 install(DIRECTORY docs/ DESTINATION "${CMAKE_INSTALL_DOCDIR}"
@@ -187,7 +187,7 @@ if(CMAKE_CROSSCOMPILING)
       "${DCMTK_RUN_CTEST_SCRIPT}" ESCAPE_QUOTES @ONLY
     )
   else()
-    # nothing to do
+    # Nothing to do
   endif()
 else()
   string(REPLACE ";" "${ENVIRONMENT_PATH_SEPARATOR}" DCMDICTPATH "${DCMTK_DICOM_DICTIONARIES}")
index 13b996d532d5a639cfa82262b608789b643c01a7..6de6e4eb7bac85163938019adde5d87fc1fa97e9 100644 (file)
--- a/COPYRIGHT
+++ b/COPYRIGHT
@@ -5,7 +5,7 @@ Unless otherwise specified, the DCMTK software package has the following
 copyright:
 
 /*
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2021, OFFIS e.V.
  *  All rights reserved.
  *
  *  This software and supporting documentation were developed by
@@ -48,6 +48,8 @@ Please note that some DCMTK modules, especially those that are not part
 of the free toolkit, are covered by a separate license which can be found
 in the COPYRIGHT file in the corresponding module directory.
 
+---------------------------------------------------------------------------
+
 Some portions of the DCMTK software package are derived from earlier
 versions of this software with the following copyright, and can be
 identified by the following copyright notice located in each source file:
@@ -99,6 +101,8 @@ identified by the following copyright notice located in each source file:
  *
  */
 
+---------------------------------------------------------------------------
+
 Some other parts of this software within the dcmtk/dcmnet sub-package
 related to the DICOM Upper Layer Protocol are derived from software
 developed for the RSNA'93 DICOM demonstration and kindly made available
@@ -138,6 +142,8 @@ source file:
  *  the copyright notice.
  */
 
+---------------------------------------------------------------------------
+
 The dcmjpeg sub-package includes an adapted version of the Independent
 JPEG Group Toolkit Version 6b, which is contained in dcmjpeg/libijg8,
 dcmjpeg/libijg12 and dcmjpeg/libijg16.  This toolkit is covered by the
@@ -181,6 +187,8 @@ Group Toolkit is located in dcmjpeg/docs/ijg_readme.txt.
  *  assumed by the product vendor.
  */
 
+---------------------------------------------------------------------------
+
 The code for the interpolatePixel() image scaling algorithm in module
 dcmimgle has been derived from code written by Jef Poskanzer for the
 "Extended Portable Bitmap Toolkit" (pbmplus10dec91) which has the
@@ -197,6 +205,8 @@ following copyright:
  * implied warranty.
  */
 
+---------------------------------------------------------------------------
+
 The color quantization code in module dcmimage (dcmquant and the related
 classes) has been derived from code written by Jef Poskanzer for the
 NetPBM toolkit which has the following copyright:
@@ -212,6 +222,8 @@ NetPBM toolkit which has the following copyright:
  * implied warranty.
  */
 
+---------------------------------------------------------------------------
+
 The code for the OFStandard::strlcpy and OFStandard::strlcat helper
 functions in ofstd/libsrc/ofstd.cc has been derived from the BSD
 implementation of strlcpy() and strlcat() and which carries the
@@ -244,6 +256,8 @@ following copyright notice:
  *  ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
 
+---------------------------------------------------------------------------
+
 The code for the OFStandard::atof helper function in ofstd/libsrc/ofstd.cc
 has been derived from an implementation which carries the following
 copyright notice:
@@ -277,6 +291,8 @@ copyright notice:
  *  WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
  */
 
+---------------------------------------------------------------------------
+
 The "Base64" encoder/decoder in ofstd/libsrc/ofstd.cc has been derived
 from an implementation which carries the following copyright notice:
 
@@ -287,6 +303,8 @@ from an implementation which carries the following copyright notice:
  *  provided the authors copyright notice remains intact.
  */
 
+---------------------------------------------------------------------------
+
 The oflog sub-package is based on the log4cplus library which is covered by
 the following two copyright notices (for details see oflog/docs/LICENSE):
 
@@ -337,6 +355,8 @@ the following two copyright notices (for details see oflog/docs/LICENSE):
 // See the License for the specific language governing permissions and
 // limitations under the License.
 
+---------------------------------------------------------------------------
+
 The dcmjpls sub-package is based on the CharLS library, which is contained
 in dcmjpls/libcharls. This toolkit is covered by the following copyright:
 
@@ -372,6 +392,8 @@ in dcmjpls/libcharls. This toolkit is covered by the following copyright:
  *  SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
 
+---------------------------------------------------------------------------
+
 The file ofstd/include/dcmtk/ofstd/oftest.h is heavily based on quicktest.h
 from the quicktest project, which is covered by the following copyright:
 
@@ -431,7 +453,7 @@ ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 
----
+---------------------------------------------------------------------------
 
 The files ofstd/include/dcmtk/ofstd/ofxml.h and ofstd/libsrc/ofxml.cc are
 derived from the XMLparser library, which is covered by the following
@@ -473,12 +495,14 @@ copyright:
  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
 
+---------------------------------------------------------------------------
+
 The dcmrt sub-package is covered by the following copyright:
 
 ---------------------------------------------------------------------------
 
 Copyright (C) 2008-2012, OFFIS e.V. and ICSMED AG, Oldenburg, Germany
-Copyright (C) 2013-2019, J. Riesmeier, Oldenburg, Germany
+Copyright (C) 2013-2021, J. Riesmeier, Oldenburg, Germany
 All rights reserved.
 
 Redistribution and use in source and binary forms, with or without
@@ -507,11 +531,13 @@ CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
 ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
 POSSIBILITY OF SUCH DAMAGE.
 
+---------------------------------------------------------------------------
+
 Parts of the dcmsr sub-package are covered by the following copyright:
 
 ---------------------------------------------------------------------------
 
-Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+Copyright (C) 2015-2021, J. Riesmeier, Oldenburg, Germany
 All rights reserved.
 
 Redistribution and use in source and binary forms, with or without
@@ -583,6 +609,8 @@ For binary libraries and executables statically linked against these
 external libraries, the following additional copyright notices /
 licenses apply:
 
+---------------------------------------------------------------------------
+
 When compiled with libiconv support:
 
 ---------------------------------------------------------------------------
diff --git a/CREDITS b/CREDITS
index 851b83533f0b2672e72ce4c99d1b5c68b1f1c662..b4a3902fe2fa8ff0376bcbc1dc0fad65970de0a3 100644 (file)
--- a/CREDITS
+++ b/CREDITS
@@ -16,6 +16,9 @@ Epilepsieforschung: The Gesellschaft fuer Epilepsieforschung e.V. (Bielefeld,
   Germany) supported the DCMTK by sponsoring the initial development of the
   tool "dcmrecv" and the underlying class "DcmStorageSCP".
 
+GE Aviation: GE Aviation supported DCMTK by sponsoring the development of the
+  dcmect library and basic concatenation support in dcmfg.
+
 ICSMED: From 2006 to 2012, the work on the DCMTK was supported by employees of
   the ICSMED AG (Oldenburg, Germany), a spin-off from the OFFIS institute.
 
@@ -58,4 +61,4 @@ YXLON: The work on the initial version of the DICONDE data dictionary was
 Please note that this list does not claim to be exhaustive.  Just send us an
 email if you think that you or your company/organization should also be listed.
 
-DCMTK Team, 2017-04-20
+DCMTK Team, 2021-01-14
diff --git a/INSTALL b/INSTALL
index 67b396ac0878d7e302981ee19d2521c4be7839cf..24f317cdc0ef73cd57a2682e1db732399beca02d 100644 (file)
--- a/INSTALL
+++ b/INSTALL
@@ -1,4 +1,3 @@
-==================================
 DICOM TOOLKIT (DCMTK) INSTALLATION
 ==================================
 
@@ -32,21 +31,28 @@ The DCMTK software can be compiled under a native Microsoft Windows environment
 The current (minor) release successfully compiles on the following operating
 system / hardware / compiler combinations:
 
-   Windows 7       / Intel x86    / Microsoft Visual C++ 2008 Express (VS 9)
    Windows 7       / Intel x86    / Microsoft Visual C++ 2010 Express (VS 10)
-   Windows 7       / Intel x86    / Microsoft Visual C++ 2012 Express (VS 11)
-   Windows 7       / Intel x86    / Microsoft Visual C++ 2013 Express (VS 12)
    Windows 7       / Intel x86    / Microsoft Visual C++ 2015 Community (VS 14)
-   Windows 7       / Intel x86    / Microsoft Visual C++ 2017 Community (VS 15)
-   Windows 7       / Intel x86    / MinGW gcc 7.4.0 (i686-w64-mingw32)
    Windows 7       / amd64|x86_64 / Microsoft Visual C++ 2010 Express (VS 10)
-   Windows 7       / amd64|x86_64 / Microsoft Visual C++ 2012 Express (VS 11)
-   Windows 7       / amd64|x86_64 / Microsoft Visual C++ 2013 Express (VS 12)
    Windows 7       / amd64|x86_64 / Microsoft Visual C++ 2015 Community (VS 14)
-   Windows 7       / amd64|x86_64 / Microsoft Visual C++ 2017 Community (VS 15)
-   Windows 7       / amd64|x86_64 / Microsoft Visual C++ 2019 Community (VS 16)
-   Windows 7       / amd64|x86_64 / MinGW gcc 8.2.1 (x86_64-w64-mingw32)
+   Windows 10      / Intel x86    / Microsoft Visual C++ 2008 Express (VS 9)
+   Windows 10      / Intel x86    / Microsoft Visual C++ 2010 Express (VS 10)
+   Windows 10      / Intel x86    / Microsoft Visual C++ 2012 Express (VS 11)
+   Windows 10      / Intel x86    / Microsoft Visual C++ 2013 Express (VS 12)
+   Windows 10      / Intel x86    / Microsoft Visual C++ 2015 Community (VS 14)
+   Windows 10      / Intel x86    / Microsoft Visual C++ 2017 Community (VS 15)
+   Windows 10      / Intel x86    / Microsoft Visual C++ 2019 Community (VS 16)
+   Windows 10      / Intel x86    / MinGW gcc 9.2.0 (i686-w64-mingw32)
+   Windows 10      / Intel x86    / MinGW gcc 10.2.0 (i686-w64-mingw32)
+   Windows 10      / Intel x86    / MinGW Clang 10.0.1 (i686-w64-mingw32)
+   Windows 10      / amd64|x86_64 / Microsoft Visual C++ 2012 Express (VS 11)
+   Windows 10      / amd64|x86_64 / Microsoft Visual C++ 2013 Express (VS 12)
+   Windows 10      / amd64|x86_64 / Microsoft Visual C++ 2015 Community (VS 14)
+   Windows 10      / amd64|x86_64 / Microsoft Visual C++ 2017 Community (VS 15)
    Windows 10      / amd64|x86_64 / Microsoft Visual C++ 2019 Community (VS 16)
+   Windows 10      / amd64|x86_64 / MinGW gcc 9.2.0 (x86_64-w64-mingw32)
+   Windows 10      / amd64|x86_64 / MinGW gcc 10.2.0 (x86_64-w64-mingw32)
+   Windows 10      / amd64|x86_64 / MinGW Clang 10.0.1 (x86_64-w64-mingw32)
 
 Unix (or lookalikes)
 --------------------
@@ -55,26 +61,34 @@ The current DCMTK software release successfully compiles on the following
 operating system / hardware / compiler combinations using the instructions
 given below:
 
-   FreeBSD 12.0    / amd64|x86_64 / Clang 6.0.1
+   FreeBSD 12.2    / amd64|x86_64 / Clang 10.0.1
    Linux 3.2.0     / amd64|x86_64 / GNU gcc 4.4.7     (Debian 7.11)
-   Linux 3.10.0    / amd64|x86_64 / Clang 3.4.2       (CentOS 7.7)
-   Linux 3.10.0    / amd64|x86_64 / GNU gcc 4.8.5     (CentOS 7.7)
+   Linux 3.10.0    / amd64|x86_64 / Clang 3.4.2       (CentOS 7.9)
+   Linux 3.10.0    / amd64|x86_64 / GNU gcc 4.8.5     (CentOS 7.9)
    Linux 3.13.0    / amd64|x86_64 / Clang 3.9.1       (Linux Mint 17.3)
    Linux 3.13.0    / amd64|x86_64 / GNU gcc 4.8.5     (Linux Mint 17.3)
    Linux 3.13.0    / amd64|x86_64 / GNU gcc 5.5.0     (Linux Mint 17.3)
    Linux 3.13.0    / amd64|x86_64 / GNU gcc 6.5.0     (Linux Mint 17.3)
-   Linux 3.13.0    / amd64|x86_64 / GNU gcc 8.3.0     (Linux Mint 17.3)
+   Linux 3.13.0    / amd64|x86_64 / GNU gcc 7.5.0     (Linux Mint 17.3)
+   Linux 3.13.0    / amd64|x86_64 / GNU gcc 8.4.0     (Linux Mint 17.3)
    Linux 4.19.0    / Intel x86    / Clang 7.0.1       (Debian 10)
    Linux 4.19.0    / Intel x86    / GNU gcc 8.3.0     (Debian 10)
    Linux 4.19.0    / amd64|x86_64 / Clang 7.0.1       (Debian 10)
    Linux 4.19.0    / amd64|x86_64 / GNU gcc 8.3.0     (Debian 10)
-   Linux 5.0.0     / amd64|x86_64 / gcc 8.3.0         (Ubuntu Linux)
-   Linux 5.3.7     / amd64|x86_64 / Clang 9.0.0       (Arch Linux)
-   Linux 5.3.7     / amd64|x86_64 / GNU gcc 9.2.0     (Arch Linux)
+   Linux 4.19.41   / amd64|x86_64 / GNU 8.3.0         (Alpine 3.9.4 with musl libc)
+   Linux 5.4.0     / amd64|x86_64 / Clang 9.0.1       (Ubuntu 20.04)
+   Linux 5.4.0     / amd64|x86_64 / Clang 10.0.0      (Ubuntu 20.04)
+   Linux 5.4.0     / amd64|x86_64 / GNU gcc 9.3.0     (Ubuntu 20.04)
+   Linux 5.4.0     / amd64|x86_64 / GNU gcc 10.2.0    (Ubuntu 20.04)
+   Linux 5.8.0     / amd64|x86_64 / GNU gcc 10.2.0    (Ubuntu 20.10)
+   Linux 5.8.0     / amd64|x86_64 / Clang 11.0.0      (Ubuntu 20.10)
    MacOS X 10.15   / amd64|x86_64 / Apple Clang 11.0.0
    MacOS X 10.15   / amd64|x86_64 / GNU gcc 9.2.0
-   OpenBSD 6.5     / amd64|x86_64 / Clang 7.0.1
-   OpenBSD 6.5     / amd64|x86_64 / GNU gcc 4.2.1
+   NetBSD 9.0      / amd64|x86_64 / Clang 9.0.1
+   NetBSD 9.0      / amd64|x86_64 / GNU gcc 7.4.0
+   OpenBSD 6.8     / amd64|x86_64 / Clang 10.0.1
+   OpenBSD 6.8     / amd64|x86_64 / GNU gcc 4.2.1
+   OpenBSD 6.8     / amd64|x86_64 / GNU gcc 8.4.0
    OpenIndiana     / Intel x86    / GNU gcc 8.3.0     (OpenIndiana 2019.04)
    Solaris 11.3    / Intel x86    / GNU gcc 4.8.2
    Solaris 11.3    / Intel x86    / SunPro CC 5.14    (Oracle Developer Studio 12.5)
@@ -86,7 +100,7 @@ Cross Compiling
 The current DCMTK release can be cross-compiled targeting the following
 platforms:
 
-  Android          / arm64        / GNU gcc 6.3.0     (API 24, ABI arm64-v8a)
+   Android         / arm64        / GNU gcc 8.3.0     (API 24, ABI arm64-v8a)
 
 Cross compiling support with running configuration and unit tests is currently
 only provided using CMake and requires the use of the Android emulator or Wine
@@ -97,6 +111,19 @@ that is being regularly tested.
 Other Platforms
 ---------------
 
+The previous minor release DCMTK 3.6.5 was also tested on the following
+platforms that may still work, but were not tested again for this minor release:
+
+   Android         / arm64        / GNU gcc 6.3.0     (API 24, ABI arm64-v8a)
+   FreeBSD 12.0    / amd64|x86_64 / Clang 6.0.1
+   Linux 5.0.0     / amd64|x86_64 / gcc 8.3.0         (Ubuntu Linux)
+   Linux 5.3.7     / amd64|x86_64 / Clang 9.0.0       (Arch Linux)
+   Linux 5.3.7     / amd64|x86_64 / GNU gcc 9.2.0     (Arch Linux)
+   OpenBSD 6.5     / amd64|x86_64 / Clang 7.0.1
+   OpenBSD 6.5     / amd64|x86_64 / GNU gcc 4.2.1
+   Windows 10      / Intel x86    / MinGW gcc 7.4.0 (i686-w64-mingw32)
+   Windows 10      / amd64|x86_64 / MinGW gcc 8.2.1 (x86_64-w64-mingw32)
+
 The previous minor release DCMTK 3.6.4 was also tested on the following
 platforms that may still work, but were not tested again for this minor release:
 
@@ -162,12 +189,19 @@ using the Transport Layer Security (TLS) protocol as defined in DICOM part 15.
 DCMTK relies on the OpenSSL toolkit (www.openssl.org) for the underlying
 cryptographic routines and the TLS protocol implementation.
 
-This release of DCMTK requires OpenSSL release 1.0.1 or newer, since older
-versions do not support the TLS 1.2 protocol required by the more recent
-DICOM security profiles.  We recommend the use of OpenSSL 1.0.2 or newer,
-however, since some optional functions recommended by RFC 7525 / BCP 195
-are only available starting with this OpenSSL release.  Furthermore, users
-should make care that the most recent OpenSSL patch level is applied.
+This release of DCMTK requires OpenSSL release 1.0.1 or newer.  We recommend
+the use of OpenSSL 1.0.2 or newer, however, since some  optional functions
+recommended by RFC 7525 / BCP 195 are only available  starting with this
+OpenSSL release.  Furthermore, users should make care that the most recent
+OpenSSL patch level is applied.  This release of DCMTK is known to compile with
+the OpenSSL releases 1.0.1 to 1.1.1i.
+
+Note: DCMTK 3.6.6 is explicitly NOT approved for use with the upcoming
+OpenSSL 3.0.0 library, which is currently in "alpha" status. OpenSSL 3.0
+will NOT work correctly with the dcmsign module, as it requires some additional
+code to load the RIPEMD160 routines, which have been moved to the so-called
+"legacy provider" that is not active by default; the required modifications
+will be included in the next DCMTK release.
 
 When using CMake, if support for security enhancements is desired, a compiled
 version of the OpenSSL libraries and include files must be available during
@@ -196,7 +230,7 @@ LIBTIFF SUPPORT
 Starting with release 3.5.1, DCMTK supports the conversion of DICOM images to
 TIFF.  DCMTK relies on the libtiff toolkit (www.libtiff.org) for this purpose.
 This release of DCMTK is known to compile with the libtiff releases 3.8.2 to
-4.10.0, although other releases may work as well.  However, libtiff releases
+4.1.0, although other releases may work as well.  However, libtiff releases
 prior to version 3.7.0 will not work since the TIFFCleanup() function was not
 yet available.  On Windows, libtiff 3.7.4 or higher is required due to
 incompatible API changes in libtiff.
@@ -224,7 +258,7 @@ LIBXML2 SUPPORT
 Starting with release 3.5.3, DCMTK supports the conversion of XML documents to
 DICOM files.  DCMTK relies on the libxml2 toolkit (www.libxml.org) for this
 purpose.  This release of DCMTK is known to compile with the libxml2 releases
-2.9.4 to 2.9.9, although other releases may work as well.
+2.9.4 to 2.9.10, although other releases may work as well.
 
 When using CMake, if support for XML import is desired, a compiled version of
 the libxml2 (and possibly iconv) libraries and include files must be available
@@ -288,8 +322,8 @@ ICU SUPPORT
 
 DCMTK supports the International Components for Unicode (ICU) library as an
 alternative to the above mentioned libiconv.  This release of DCMTK is known to
-compile with the ICU releases 59.1 to 65.1, although other releases may work as
-well.
+compile with the ICU releases 59.1 to 68.1.0, although other releases may work
+as well.
 
 The ICU may be easier to integrate on some more modern Linux distributions
 (e.g. Arch Linux) and Windows than the libiconv but (due to the way it is
@@ -363,13 +397,13 @@ respectively: use "--enable-stl-<feature>", "--disable-stl-<feature>" and/or
 SUPPORT FOR MODERN C++ STANDARDS
 ================================
 
-DCMTK can be configured to use several features of modern C++ standards, eg.
-(e.g. C++11 move semantics, variadic templates and the like) instead of its own
+DCMTK can be configured to use several features of modern C++ standards (e.g.
+C++11 move semantics, variadic templates and the like) instead of its own
 workarounds and fallback implementations.  This can be achieved using CMake's
 variables "CMAKE_CXX_STANDARD" and "CMAKE_CXX_STANDARD_REQUIRED".
 The previous mechanism only handled C++11 and is available on old versions of
-CMake (versions prior 3.1.3): set "DCMTK_ENABLE_CXX11" to "ON". For Autoconf,
-use the "--enable-cxx11" argument. Both the "DCMTK_ENABLE_CXX11" variable and
+CMake (versions prior 3.1.3): set "DCMTK_ENABLE_CXX11" to "ON".  For Autoconf,
+use the "--enable-cxx11" argument.  Both the "DCMTK_ENABLE_CXX11" variable and
 Autoconf support are now deprecated and will be removed in a future release.
 
 Enabling e.g. C++11 will change some parts of DCMTK's API, so a C++11 build of
@@ -399,8 +433,8 @@ directories.  In detail, these "CMakeLists.txt" files will serve as an input to
 CMake which will generate suitable build files for all of DCMTK's projects from
 these files.
 
-DCMTK 3.6.5 requires CMake version 2.8.5 or later.  We recommend using the
-latest stable release of CMake (currently version 3.15.4) since newer versions
+DCMTK 3.6.6 requires CMake version 2.8.5 or later.  We recommend using the
+latest stable release of CMake (currently version 3.19.2) since newer versions
 of CMake often provide better output in case of errors and are generally easier
 to use (for example by providing better support for detecting the availability
 of third party libraries).  If possible, use the CMake version your operating
@@ -416,7 +450,7 @@ CMake and shared libraries
 The CMake build system allows for building shared libraries instead of static
 libraries.  On Windows systems, these are dynamic link libraries (.dll).
 On Unix systems, these are shared objects (.so).  To enable this, set the
-"BUILD_SHARED_LIB" option to "ON".
+"BUILD_SHARED_LIBS" option to "ON".
 
 Additionally, it is possible to produce a single shared library for the whole
 toolkit.  This mode is controlled by the "BUILD_SINGLE_SHARED_LIBRARY" option.
@@ -484,7 +518,7 @@ CMake, perform the following steps:
 1. Go Start -> Programs -> CMake -> "CMake" or "CMake (cmake-gui)" to start the
    CMake utility through which the configuration can be done.
 2. In the entry field "Where is the source code:" enter the directory in which
-   the DCMTK source code resides, e.g. "C:\dcmtk-3.6.5".
+   the DCMTK source code resides, e.g. "C:\dcmtk-3.6.6".
 3. In the entry field "Where to build the binaries:" enter the directory in
    which the libraries and binaries are to be built, e.g. "C:\dcmtk-msvc15".
 4. In the combobox "Build for:" or "Specify the generator for this project:"
@@ -507,11 +541,11 @@ CMake, perform the following steps:
 
      libtiff support:
        set "DCMTK_WITH_TIFF" to "ON" and
-       set "WITH_LIBTIFFINC" e.g. to "C:\libtiff-4.0.10"
+       set "WITH_LIBTIFFINC" e.g. to "C:\libtiff-4.1.0"
 
      OpenSSL support:
        set "DCMTK_WITH_OPENSSL" to "ON" and
-       set "WITH_OPENSSLINC" e.g. to "C:\openssl-1.1.1d"
+       set "WITH_OPENSSLINC" e.g. to "C:\openssl-1.1.1i"
 
      zlib support:
        set "DCMTK_WITH_ZLIB" to "ON" and
@@ -519,7 +553,7 @@ CMake, perform the following steps:
 
      libiconv support:
        set "DCMTK_WITH_ICONV" to "ON" and
-       set "WITH_LIBICONVINC" e.g. to "C:\libiconv-1.15"
+       set "WITH_LIBICONVINC" e.g. to "C:\libiconv-1.16"
 
    In order to turn the support of a certain external library off, set the
    value of the corresponding variable ("DCMTK_WITH_XML", "DCMTK_WITH_PNG",
@@ -578,6 +612,30 @@ CMake, perform the following steps:
    for the non-debug multithread runtime (/MT).  Precompiled versions of all
    libraries can be downloaded from https://www.dcmtk.org/dcmtk#lib-win.
 
+   In the CMake GUI, there are a few more settings that can be modified
+   to affect the way DCMTK is compiled. The most important of these are:
+
+    - DCMTK_OVERWRITE_WIN32_COMPILER_FLAGS: By default, DCMTK will compile
+      using the default compiler options selected by CMake. When this macro
+      is enabled, these default options are modified based on the value
+      of the DCMTK_COMPILE_WIN32_MULTITHREADED_DLL setting (see below).
+      Default: ON.
+    - DCMTK_COMPILE_WIN32_MULTITHREADED_DLL: Controls the Windows build
+      model. When this setting is ON, DCMTK compiled with the
+      "Multithreaded DLL" build model (/MD or /MDd); when the setting is
+      OFF, DCMTK is compiled with the "Multithreaded" build model
+      (/MT or /MTd). This setting is ignored unless the
+      DCMTK_OVERWRITE_WIN32_COMPILER_FLAGS option is ON.
+      Default: OFF.
+    - BUILD_SHARED_LIBS: Build the DCMTK libraries as shared libraries.
+      This setting overrides the value of the options
+      DCMTK_OVERWRITE_WIN32_COMPILER_FLAGS and
+      DCMTK_COMPILE_WIN32_MULTITHREADED_DLL, which are both set to ON.
+      Default: OFF.
+    - BUILD_SINGLE_SHARED_LIBRARY: Build a single shared library for the
+      whole toolkit. This setting overrides the value of the option
+      BUILD_SHARED_LIBS, which is set to ON. Default: OFF.
+
 7. Go "Configure" a second time.  (CMake will adjust the configuration
    according to the displayed specifications.)
 8. Go "OK" or "Generate".  (CMake will generate new project files in the
@@ -613,10 +671,6 @@ Known limitations of DCMTK on the Windows platform.
    DCMTK can be configured to use either of the two interfaces.  This behavior
    can be changed in "config/include/dcmtk/config/osconfig.h" in the build
    directory where the symbol USE_STD_CXX_INCLUDES is declared.
-3. DCMTK does not compile when UNICODE or _UNICODE is defined because the
-   VisualStudio compiler then uses the Unicode version instead of the ANSI
-   version for all Windows API functions (i.e. type wchar_t instead of char
-   for all character string parameters and return values).
 
 
 Unix with CMake
@@ -638,18 +692,18 @@ https://cmake.org/cmake/help/latest/module/FindZLIB.html .
 The typical way to build DCMTK on Unix like systems with CMake is as follows
 (if not using the GUI, in that case look at the description for Windows above):
 
-    mkdir dcmtk-3.6.5-build
-    cd dcmtk-3.6.5-build
-    cmake ../dcmtk-3.6.5
+    mkdir dcmtk-3.6.6-build
+    cd dcmtk-3.6.6-build
+    cmake ../dcmtk-3.6.6
     make -j8
-    make DESTDIR=../dcmtk-3.6.5-install install
+    make DESTDIR=../dcmtk-3.6.6-install install
 
 The above commands assume that the DCMTK source code was extracted to the
-current working directory into a folder named dcmtk-3.6.5.  DCMTK will be
+current working directory into a folder named dcmtk-3.6.6.  DCMTK will be
 configured using CMake with the default options, detecting and including all
 available support libraries and then compiled using eight CPU cores
 ('make -j8', adjust as needed).  The result will be installed to the directory
-"dcmtk-3.6.5-install" next to the source code directory.
+"dcmtk-3.6.6-install" next to the source code directory.
 
 If you want to modify your build configuration, like enabling or disabling
 some features of DCMTK (e.g. PNG support), or if you need to modify the
@@ -657,10 +711,10 @@ predefined build-variables, you can use the curses based cmake configuration
 tool 'ccmake'.  First, create the initial build setup (system check) and then
 call ccmake:
 
-    mkdir dcmtk-3.6.5-build
-    cd dcmtk-3.6.5-build
-    cmake ../dcmtk-3.6.5
-    ccmake ../dcmtk-3.6.5
+    mkdir dcmtk-3.6.6-build
+    cd dcmtk-3.6.6-build
+    cmake ../dcmtk-3.6.6
+    ccmake ../dcmtk-3.6.6
 
 Now you can modify the configuration values.  Please see the help on the bottom
 of the screen.  When finished, press 'c' to generate a new build configuration,
@@ -670,9 +724,9 @@ If you already know the variable names, types and values to set, you can skip
 the 'ccmake' step above and can call 'cmake' directly with the values set.
 Example for a build with TCP wrapper disabled:
 
-    mkdir dcmtk-3.6.5-build
-    cd dcmtk-3.6.5-build
-    cmake -DDCMTK_WITH_WRAP:BOOL=FALSE ../dcmtk-3.6.5
+    mkdir dcmtk-3.6.6-build
+    cd dcmtk-3.6.6-build
+    cmake -DDCMTK_WITH_WRAP:BOOL=FALSE ../dcmtk-3.6.6
     ...
 
 The format is NAME:TYPE=VALUE.  Use 'ccmake' to find out the variable names and
@@ -699,16 +753,16 @@ HTML DOCUMENTATION AND MAN PAGES
 Most DCMTK modules have been documented with Doxygen (www.doxygen.org), a free
 source code documentation system similar to Javadoc.  Unix users who have
 Doxygen installed can create a hypertext documentation with "make html" in the
-"dcmtk-3.6.5" or "doxygen" directory; Windows and other CMake users should
+"dcmtk-3.6.6" or "doxygen" directory; Windows and other CMake users should
 build the "DOXYGEN" subproject.  A project file for Microsoft's HTML Help
 Workshop can also be generated allowing to create a single CHM file (compressed
 HTML) from the documentation.  Other output formats (e.g. LaTeX) can be enabled
 by changing the configuration file in the "doxygen" directory.
 
-At the current time, dcmfg, dcmiod, dcmimage, dcmimgle, dcmjpeg, dcmpmap,
-dcmpstat, dcmrt, dcmseg, dcmsign, dcmsr, dcmtls, dcmtract, dcmwlm and ofstd are
-completely documented; dcmdata, dcmjpls, dcmnet and oflog are almost completely
-documented.  See FAQ entry: "Where is rest of the documentation?"
+At the current time, dcmect, dcmfg, dcmiod, dcmimage, dcmimgle, dcmjpeg,
+dcmpmap, dcmpstat, dcmrt, dcmseg, dcmsign, dcmsr, dcmtls, dcmtract, dcmwlm and
+ofstd are completely documented; dcmdata, dcmjpls, dcmnet and oflog are almost
+completely documented.  See FAQ entry: "Where is rest of the documentation?"
 
 On Unix platforms, man pages for all command line tools are installed during
 the "make install" step.  In order to use them, just add the directory (e.g.
@@ -776,11 +830,11 @@ BUILDING (Unix with Autoconf)
 =============================
 
 Configuring a DCMTK build with GNU Autoconf has been deprecated with DCMTK
-release 3.6.5 and will be removed in future releases.  In the current release,
+release 3.6.6 and will be removed in future releases.  In the current release,
 the "configure" script in DCMTK's top-level main directory has been removed
 as the final warning for users of the Autoconf toolchain.  If you prefer to
 build DCMTK with Autoconf, however, this is still possible.  Perform the
-following steps from the top-level (dcmtk-3.6.5) directory to compile and
+following steps from the top-level (dcmtk-3.6.6) directory to compile and
 install the software:
 
 Step 0:
@@ -811,15 +865,15 @@ in which OpenSSL is installed.  This is usually the directory that has been
 used as --prefix when compiling and installing OpenSSL.
 
 For example, if you wish to enable the security enhancements, and OpenSSL is
-installed in "/usr/local/apps/openssl-1.1.1d", then you should start configure
+installed in "/usr/local/apps/openssl-1.1.1i", then you should start configure
 as:
 
     ./configure --ignore-deprecation
-                --with-opensslinc=/usr/local/apps/openssl-1.1.1d
+                --with-opensslinc=/usr/local/apps/openssl-1.1.1i
 
 Configure will assume that the OpenSSL include files are installed in
-"/usr/local/apps/openssl-1.1.1d/include" and will expect the library in
-"/usr/local/apps/openssl-1.1.1d/lib".  Appropriate options will be passed to
+"/usr/local/apps/openssl-1.1.1i/include" and will expect the library in
+"/usr/local/apps/openssl-1.1.1i/lib".  Appropriate options will be passed to
 the compiler and the linker.
 
 Support for zlib, libtiff, libpng, libxml2, libwrap and libiconv can be enabled
@@ -828,13 +882,13 @@ path):
 
     ./configure --ignore-deprecation
                 --with-libzlibinc=/usr/local/apps/zlib-1.2.11
-                --with-libtiffinc=/usr/local/apps/libtiff-4.0.10
+                --with-libtiffinc=/usr/local/apps/libtiff-4.1.0
                 --with-libpnginc=/usr/local/apps/libpng-1.6.37
-                --with-libxmlinc=/usr/local/apps/libxml2-2.9.9
+                --with-libxmlinc=/usr/local/apps/libxml2-2.9.10
                 --with-libwrapinc=/usr/local/apps/tcp_wrappers-7.6
-                --with-libiconvinc=/usr/local/apps/libiconv-1.15
+                --with-libiconvinc=/usr/local/apps/libiconv-1.16
            <or>
-                --with-libicuinc=/usr/local/apps/icu-65.1
+                --with-libicuinc=/usr/local/apps/icu-68.1.0
 
 Different configure options can be combined in any order.  configure --help
 will print a list of all existing configure options.  configure --help=short
@@ -934,4 +988,4 @@ Have fun.
 M. Eichelberg, J. Riesmeier, M. Onken, J. Schlamelcher, P. Arizpe Gomez
 DCMTK Development Team, Oldenburg, Germany.
 
-Last revised: 2019-10-28 (Schlamelcher)
+Last revised: 2021-01-14 (Onken)
index 84ee6b0d9c906266282f9ff031ab129926cc7265..eec613249a7f458b14edd9097fde3cfca5334c6a 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -9,43 +9,43 @@ include $(configdir)/Makefile.def
 
 .NOTPARALLEL:
 
-all:  config-all ofstd-all oflog-all dcmdata-all dcmiod-all dcmfg-all dcmseg-all dcmimgle-all dcmimage-all dcmjpeg-all dcmjpls-all dcmtls-all dcmnet-all dcmsr-all dcmsign-all dcmwlm-all dcmqrdb-all dcmpstat-all dcmrt-all dcmtract-all dcmpmap-all
+all:  config-all ofstd-all oflog-all dcmdata-all dcmiod-all dcmfg-all dcmseg-all dcmimgle-all dcmimage-all dcmjpeg-all dcmjpls-all dcmtls-all dcmnet-all dcmsr-all dcmsign-all dcmwlm-all dcmqrdb-all dcmpstat-all dcmrt-all dcmtract-all dcmpmap-all dcmect-all
 
-libsrc-all:  ofstd-libsrc-all oflog-libsrc-all dcmdata-libsrc-all dcmiod-libsrc-all dcmfg-libsrc-all dcmseg-libsrc-all dcmimgle-libsrc-all dcmimage-libsrc-all dcmjpeg-libsrc-all dcmjpls-libsrc-all dcmtls-libsrc-all dcmnet-libsrc-all dcmsr-libsrc-all dcmsign-libsrc-all dcmwlm-libsrc-all dcmqrdb-libsrc-all dcmpstat-libsrc-all dcmrt-libsrc-all dcmtract-libsrc-all dcmpmap-libsrc-all
+libsrc-all:  ofstd-libsrc-all oflog-libsrc-all dcmdata-libsrc-all dcmiod-libsrc-all dcmfg-libsrc-all dcmseg-libsrc-all dcmimgle-libsrc-all dcmimage-libsrc-all dcmjpeg-libsrc-all dcmjpls-libsrc-all dcmtls-libsrc-all dcmnet-libsrc-all dcmsr-libsrc-all dcmsign-libsrc-all dcmwlm-libsrc-all dcmqrdb-libsrc-all dcmpstat-libsrc-all dcmrt-libsrc-all dcmtract-libsrc-all dcmpmap-libsrc-all dcmect-libsrc-all
 
-tests-all:  config-tests-all ofstd-tests-all oflog-tests-all dcmdata-tests-all dcmiod-tests-all dcmfg-tests-all dcmseg-tests-all dcmimgle-tests-all dcmimage-tests-all dcmjpeg-tests-all dcmjpls-tests-all dcmtls-tests-all dcmnet-tests-all dcmsr-tests-all dcmsign-tests-all dcmwlm-tests-all dcmqrdb-tests-all dcmpstat-tests-all dcmrt-tests-all dcmtract-tests-all dcmpmap-tests-all
+tests-all:  config-tests-all ofstd-tests-all oflog-tests-all dcmdata-tests-all dcmiod-tests-all dcmfg-tests-all dcmseg-tests-all dcmimgle-tests-all dcmimage-tests-all dcmjpeg-tests-all dcmjpls-tests-all dcmtls-tests-all dcmnet-tests-all dcmsr-tests-all dcmsign-tests-all dcmwlm-tests-all dcmqrdb-tests-all dcmpstat-tests-all dcmrt-tests-all dcmtract-tests-all dcmpmap-tests-all dcmect-tests-all
 
-install:  config-install ofstd-install oflog-install dcmdata-install dcmiod-install dcmfg-install dcmseg-install dcmimgle-install dcmimage-install dcmjpeg-install dcmjpls-install dcmtls-install dcmnet-install dcmsr-install dcmsign-install dcmwlm-install dcmqrdb-install dcmpstat-install dcmrt-install dcmtract-install dcmpmap-install dcmtk-install-doc install-man
+install:  config-install ofstd-install oflog-install dcmdata-install dcmiod-install dcmfg-install dcmseg-install dcmimgle-install dcmimage-install dcmjpeg-install dcmjpls-install dcmtls-install dcmnet-install dcmsr-install dcmsign-install dcmwlm-install dcmqrdb-install dcmpstat-install dcmrt-install dcmtract-install dcmpmap-install dcmect-install dcmtk-install-doc install-man
 
 install-all: install install-lib install-html
 
-install-bin:  config-install-bin ofstd-install-bin oflog-install-bin dcmdata-install-bin dcmiod-install-bin dcmfg-install-bin dcmseg-install-bin dcmimgle-install-bin dcmimage-install-bin dcmjpeg-install-bin dcmjpls-install-bin dcmtls-install-bin dcmnet-install-bin dcmsr-install-bin dcmsign-install-bin dcmwlm-install-bin dcmqrdb-install-bin dcmpstat-install-bin dcmrt-install-bin dcmtract-install-bin dcmpmap-install-bin
+install-bin:  config-install-bin ofstd-install-bin oflog-install-bin dcmdata-install-bin dcmiod-install-bin dcmfg-install-bin dcmseg-install-bin dcmimgle-install-bin dcmimage-install-bin dcmjpeg-install-bin dcmjpls-install-bin dcmtls-install-bin dcmnet-install-bin dcmsr-install-bin dcmsign-install-bin dcmwlm-install-bin dcmqrdb-install-bin dcmpstat-install-bin dcmrt-install-bin dcmtract-install-bin dcmpmap-install-bin dcmect-install-bin
 
-install-doc:  config-install-doc ofstd-install-doc oflog-install-doc dcmdata-install-doc dcmiod-install-doc dcmfg-install-doc dcmseg-install-doc dcmimgle-install-doc dcmimage-install-doc dcmjpeg-install-doc dcmjpls-install-doc dcmtls-install-doc dcmnet-install-doc dcmsr-install-doc dcmsign-install-doc dcmwlm-install-doc dcmqrdb-install-doc dcmpstat-install-doc dcmrt-install-doc dcmtract-install-doc dcmpmap-install-doc
+install-doc:  config-install-doc ofstd-install-doc oflog-install-doc dcmdata-install-doc dcmiod-install-doc dcmfg-install-doc dcmseg-install-doc dcmimgle-install-doc dcmimage-install-doc dcmjpeg-install-doc dcmjpls-install-doc dcmtls-install-doc dcmnet-install-doc dcmsr-install-doc dcmsign-install-doc dcmwlm-install-doc dcmqrdb-install-doc dcmpstat-install-doc dcmrt-install-doc dcmtract-install-doc dcmpmap-install-doc dcmect-install-doc
 
-install-data:  config-install-data ofstd-install-data oflog-install-data dcmdata-install-data dcmiod-install-data dcmfg-install-data dcmseg-install-data dcmimgle-install-data dcmimage-install-data dcmjpeg-install-data dcmjpls-install-data dcmtls-install-data dcmnet-install-data dcmsr-install-data dcmsign-install-data dcmwlm-install-data dcmqrdb-install-data dcmpstat-install-data dcmrt-install-data dcmtract-install-data dcmpmap-install-data
+install-data:  config-install-data ofstd-install-data oflog-install-data dcmdata-install-data dcmiod-install-data dcmfg-install-data dcmseg-install-data dcmimgle-install-data dcmimage-install-data dcmjpeg-install-data dcmjpls-install-data dcmtls-install-data dcmnet-install-data dcmsr-install-data dcmsign-install-data dcmwlm-install-data dcmqrdb-install-data dcmpstat-install-data dcmrt-install-data dcmtract-install-data dcmpmap-install-data dcmect-install-data
 
-install-etc:  config-install-etc ofstd-install-etc oflog-install-etc dcmdata-install-etc dcmiod-install-etc dcmfg-install-etc dcmseg-install-etc dcmimgle-install-etc dcmimage-install-etc dcmjpeg-install-etc dcmjpls-install-etc dcmtls-install-etc dcmnet-install-etc dcmsr-install-etc dcmsign-install-etc dcmwlm-install-etc dcmqrdb-install-etc dcmpstat-install-etc dcmrt-install-etc dcmtract-install-etc dcmpmap-install-etc
+install-etc:  config-install-etc ofstd-install-etc oflog-install-etc dcmdata-install-etc dcmiod-install-etc dcmfg-install-etc dcmseg-install-etc dcmimgle-install-etc dcmimage-install-etc dcmjpeg-install-etc dcmjpls-install-etc dcmtls-install-etc dcmnet-install-etc dcmsr-install-etc dcmsign-install-etc dcmwlm-install-etc dcmqrdb-install-etc dcmpstat-install-etc dcmrt-install-etc dcmtract-install-etc dcmpmap-install-etc dcmect-install-etc
 
-install-lib:  config-install-lib ofstd-install-lib oflog-install-lib dcmdata-install-lib dcmiod-install-lib dcmfg-install-lib dcmseg-install-lib dcmimgle-install-lib dcmimage-install-lib dcmjpeg-install-lib dcmjpls-install-lib dcmtls-install-lib dcmnet-install-lib dcmsr-install-lib dcmsign-install-lib dcmwlm-install-lib dcmqrdb-install-lib dcmpstat-install-lib dcmrt-install-lib dcmtract-install-lib dcmpmap-install-lib
+install-lib:  config-install-lib ofstd-install-lib oflog-install-lib dcmdata-install-lib dcmiod-install-lib dcmfg-install-lib dcmseg-install-lib dcmimgle-install-lib dcmimage-install-lib dcmjpeg-install-lib dcmjpls-install-lib dcmtls-install-lib dcmnet-install-lib dcmsr-install-lib dcmsign-install-lib dcmwlm-install-lib dcmqrdb-install-lib dcmpstat-install-lib dcmrt-install-lib dcmtract-install-lib dcmpmap-install-lib dcmect-install-lib
 
-install-include:  config-install-include ofstd-install-include oflog-install-include dcmdata-install-include dcmiod-install-include dcmfg-install-include dcmseg-install-include dcmimgle-install-include dcmimage-install-include dcmjpeg-install-include dcmjpls-install-include dcmtls-install-include dcmnet-install-include dcmsr-install-include dcmsign-install-include dcmwlm-install-include dcmqrdb-install-include dcmpstat-install-include dcmrt-install-include dcmtract-install-include dcmpmap-install-include
+install-include:  config-install-include ofstd-install-include oflog-install-include dcmdata-install-include dcmiod-install-include dcmfg-install-include dcmseg-install-include dcmimgle-install-include dcmimage-install-include dcmjpeg-install-include dcmjpls-install-include dcmtls-install-include dcmnet-install-include dcmsr-install-include dcmsign-install-include dcmwlm-install-include dcmqrdb-install-include dcmpstat-install-include dcmrt-install-include dcmtract-install-include dcmpmap-install-include dcmect-install-include
 
-install-support:  config-install-support ofstd-install-support oflog-install-support dcmdata-install-support dcmiod-install-support dcmfg-install-support dcmseg-install-support dcmimgle-install-support dcmimage-install-support dcmjpeg-install-support dcmjpls-install-support dcmtls-install-support dcmnet-install-support dcmsr-install-support dcmsign-install-support dcmwlm-install-support dcmqrdb-install-support dcmpstat-install-support dcmrt-install-support dcmtract-install-support dcmpmap-install-support
+install-support:  config-install-support ofstd-install-support oflog-install-support dcmdata-install-support dcmiod-install-support dcmfg-install-support dcmseg-install-support dcmimgle-install-support dcmimage-install-support dcmjpeg-install-support dcmjpls-install-support dcmtls-install-support dcmnet-install-support dcmsr-install-support dcmsign-install-support dcmwlm-install-support dcmqrdb-install-support dcmpstat-install-support dcmrt-install-support dcmtract-install-support dcmpmap-install-support dcmect-install-support
 
 check: tests-all
        $(MAKE) -s check-nosilent
 
-check-nosilent:  config-check ofstd-check oflog-check dcmdata-check dcmiod-check dcmfg-check dcmseg-check dcmimgle-check dcmimage-check dcmjpeg-check dcmjpls-check dcmtls-check dcmnet-check dcmsr-check dcmsign-check dcmwlm-check dcmqrdb-check dcmpstat-check dcmrt-check dcmtract-check dcmpmap-check
+check-nosilent:  config-check ofstd-check oflog-check dcmdata-check dcmiod-check dcmfg-check dcmseg-check dcmimgle-check dcmimage-check dcmjpeg-check dcmjpls-check dcmtls-check dcmnet-check dcmsr-check dcmsign-check dcmwlm-check dcmqrdb-check dcmpstat-check dcmrt-check dcmtract-check dcmpmap-check dcmect-check
 
 check-exhaustive: tests-all
        $(MAKE) -s check-nosilent-exhaustive
 
-check-nosilent-exhaustive:  config-check-exhaustive ofstd-check-exhaustive oflog-check-exhaustive dcmdata-check-exhaustive dcmiod-check-exhaustive dcmfg-check-exhaustive dcmseg-check-exhaustive dcmimgle-check-exhaustive dcmimage-check-exhaustive dcmjpeg-check-exhaustive dcmjpls-check-exhaustive dcmtls-check-exhaustive dcmnet-check-exhaustive dcmsr-check-exhaustive dcmsign-check-exhaustive dcmwlm-check-exhaustive dcmqrdb-check-exhaustive dcmpstat-check-exhaustive dcmrt-check-exhaustive dcmtract-check-exhaustive dcmpmap-check-exhaustive
+check-nosilent-exhaustive:  config-check-exhaustive ofstd-check-exhaustive oflog-check-exhaustive dcmdata-check-exhaustive dcmiod-check-exhaustive dcmfg-check-exhaustive dcmseg-check-exhaustive dcmimgle-check-exhaustive dcmimage-check-exhaustive dcmjpeg-check-exhaustive dcmjpls-check-exhaustive dcmtls-check-exhaustive dcmnet-check-exhaustive dcmsr-check-exhaustive dcmsign-check-exhaustive dcmwlm-check-exhaustive dcmqrdb-check-exhaustive dcmpstat-check-exhaustive dcmrt-check-exhaustive dcmtract-check-exhaustive dcmpmap-check-exhaustive dcmect-check-exhaustive
 
 dcmtk-install-doc:
        $(configdir)/mkinstalldirs $(DESTDIR)$(docdir)
-       for file in ANNOUNCE CHANGES COPYRIGHT CREDITS FAQ HISTORY VERSION docs/CHANGES.???; do \
+       for file in ANNOUNCE COPYRIGHT CREDITS FAQ HISTORY VERSION docs/CHANGES.???; do \
                $(INSTALL_DATA) $$file $(DESTDIR)$(docdir) ;\
        done
 
@@ -91,7 +91,7 @@ help:
        @echo ""
        @echo "The following modules are available:"
        @echo ""
-       @echo "ofstd oflog dcmdata dcmiod dcmfg dcmseg dcmimgle dcmimage dcmjpeg dcmjpls dcmtls dcmnet dcmsr dcmsign dcmwlm dcmqrdb dcmpstat dcmrt dcmtract dcmpmap"
+       @echo "ofstd oflog dcmdata dcmiod dcmfg dcmseg dcmimgle dcmimage dcmjpeg dcmjpls dcmtls dcmnet dcmsr dcmsign dcmwlm dcmqrdb dcmpstat dcmrt dcmtract dcmpmap dcmect"
 
 config-all:
        (cd config && $(MAKE) ARCH="$(ARCH)" DESTDIR="$(DESTDIR)" all)
@@ -912,6 +912,45 @@ dcmpmap-check:
 dcmpmap-check-exhaustive:
        (cd dcmpmap && $(MAKE) ARCH="$(ARCH)" DESTDIR="$(DESTDIR)" check-exhaustive)
 
+dcmect-all:
+       (cd dcmect && $(MAKE) ARCH="$(ARCH)" DESTDIR="$(DESTDIR)" all)
+
+dcmect-libsrc-all:
+       (cd dcmect && $(MAKE) ARCH="$(ARCH)" DESTDIR="$(DESTDIR)" libsrc-all)
+
+dcmect-tests-all:
+       (cd dcmect && $(MAKE) ARCH="$(ARCH)" DESTDIR="$(DESTDIR)" tests-all)
+
+dcmect-install:
+       (cd dcmect && $(MAKE) ARCH="$(ARCH)" DESTDIR="$(DESTDIR)" install)
+
+dcmect-install-bin:
+       (cd dcmect && $(MAKE) ARCH="$(ARCH)" DESTDIR="$(DESTDIR)" install-bin)
+
+dcmect-install-doc:
+       (cd dcmect && $(MAKE) ARCH="$(ARCH)" DESTDIR="$(DESTDIR)" install-doc)
+
+dcmect-install-data:
+       (cd dcmect && $(MAKE) ARCH="$(ARCH)" DESTDIR="$(DESTDIR)" install-data)
+
+dcmect-install-etc:
+       (cd dcmect && $(MAKE) ARCH="$(ARCH)" DESTDIR="$(DESTDIR)" install-etc)
+
+dcmect-install-lib:
+       (cd dcmect && $(MAKE) ARCH="$(ARCH)" DESTDIR="$(DESTDIR)" install-lib)
+
+dcmect-install-include:
+       (cd dcmect && $(MAKE) ARCH="$(ARCH)" DESTDIR="$(DESTDIR)" install-include)
+
+dcmect-install-support:
+       (cd dcmect && $(MAKE) ARCH="$(ARCH)" DESTDIR="$(DESTDIR)" install-support)
+
+dcmect-check:
+       (cd dcmect && $(MAKE) ARCH="$(ARCH)" DESTDIR="$(DESTDIR)" check)
+
+dcmect-check-exhaustive:
+       (cd dcmect && $(MAKE) ARCH="$(ARCH)" DESTDIR="$(DESTDIR)" check-exhaustive)
+
 dependencies:
        -(cd config && $(MAKE) dependencies)
        (cd ofstd && $(MAKE) dependencies)
@@ -934,6 +973,7 @@ dependencies:
        (cd dcmrt && $(MAKE) dependencies)
        (cd dcmtract && $(MAKE) dependencies)
        (cd dcmpmap && $(MAKE) dependencies)
+       (cd dcmect && $(MAKE) dependencies)
 
 clean:
        (cd ofstd && $(MAKE) clean)
@@ -956,6 +996,7 @@ clean:
        (cd dcmrt && $(MAKE) clean)
        (cd dcmtract && $(MAKE) clean)
        (cd dcmpmap && $(MAKE) clean)
+       (cd dcmect && $(MAKE) clean)
        (cd doxygen && $(MAKE) clean)
        -(cd config && $(MAKE) clean)
        rm -f $(TRASH)
@@ -981,6 +1022,7 @@ distclean:
        (cd dcmrt && $(MAKE) distclean)
        (cd dcmtract && $(MAKE) distclean)
        (cd dcmpmap && $(MAKE) distclean)
+       (cd dcmect && $(MAKE) distclean)
        (cd doxygen && $(MAKE) distclean)
        -(cd config && $(MAKE) distclean)
        rm -f $(TRASH)
diff --git a/README b/README
index 5dcb0ff659120b6ced78de28208900681a36b31d..3d5960dd3d8bb37a53fb633f4d0400e1ca09e6d2 100644 (file)
--- a/README
+++ b/README
@@ -9,6 +9,7 @@ DCMTK contains the following sub-packages, each in its own sub-directory:
 
     config   - configuration utilities for DCMTK
     dcmdata  - a data encoding/decoding library and utility apps
+    dcmect   - a library for working with Enhanced CT objects
     dcmfg    - a library for working with functional groups
     dcmimage - adds support for color images to dcmimgle
     dcmimgle - an image processing library and utility apps
index 5184478322a229377e23048a61b9ea4dbdf1043e..fbe1a3f5fb7c849e2c175c93f2bdd08b4c77d7f9 100644 (file)
--- a/README.md
+++ b/README.md
@@ -6,6 +6,7 @@ DCMTK contains the following sub-packages, each in its own sub-directory:
 
 - **config**   - configuration utilities for DCMTK
 - **dcmdata**  - a data encoding/decoding library and utility apps
+- **dcmect**   - a library for working with Enhanced CT objects
 - **dcmfg**    - a library for working with functional groups
 - **dcmimage** - adds support for color images to dcmimgle
 - **dcmimgle** - an image processing library and utility apps
@@ -28,10 +29,10 @@ DCMTK contains the following sub-packages, each in its own sub-directory:
 
 Each sub-directory (except _config_) contains further sub-directories for application source code (_apps_), library source code (_libsrc_), library include files (_include_), configuration data (_etc_), documentation (_docs_), sample and support data (_data_) as well as test programs (_tests_).
 
-To build and install the DCMTK package see the [INSTALL](INSTALL) file.  For copyright information see the [COPYRIGHT](COPYRIGHT) file.  For information about the history of this software see the [HISTORY](HISTORY) file.  For answers to frequently asked questions please consult the [FAQ](http://forum.dcmtk.org/faq/).
+To build and install the DCMTK package see the [INSTALL](INSTALL) file.  For copyright information see the [COPYRIGHT](COPYRIGHT) file.  For information about the history of this software see the [HISTORY](HISTORY) file.  For answers to frequently asked questions please consult the [FAQ](https://forum.dcmtk.org/faq/).
 
-In addition to the API documentation, which is also available [online](https://support.dcmtk.org/docs/), there is a [Wiki](http://support.dcmtk.org/wiki/) system where further information (e.g. HOWTOs) can be found.
+In addition to the API documentation, which is also available [online](https://support.dcmtk.org/docs/), there is a [Wiki](https://support.dcmtk.org/wiki/) system where further information (e.g. HOWTOs) can be found.
 
 If you find bugs or other problems with this software, we would appreciate hearing about them.  Please send electronic mail to: bugs/at/dcmtk/dot/org
 
-Please try to describe the problem in detail and if possible give a suggested fix.  For general questions on how to compile, install or use the toolkit we recommend the [public discussion forum](http://forum.dcmtk.org/).
+Please try to describe the problem in detail and if possible give a suggested fix.  For general questions on how to compile, install or use the toolkit we recommend the [public discussion forum](https://forum.dcmtk.org/).
diff --git a/VERSION b/VERSION
index d15b8b06fa347d6fdb062184febdbe5fef95c4ad..4f2c1d15f6df48073057472403968720cb96e72b 100644 (file)
--- a/VERSION
+++ b/VERSION
@@ -1 +1 @@
-3.6.5
+3.6.6
index 4641a4c0279452c75e7f6aba0796b605593a1f90..0520105061ff5702967573837f0015cd9fc4db86 100644 (file)
@@ -1182,35 +1182,6 @@ else
 fi
 ])
 
-
-dnl AC_CHECK_CXX_BOOL checks if bool is a built-in C++ type
-dnl   (which is not the case on older compilers).
-
-dnl AC_CHECK_CXX_BOOL(ACTION-IF-FOUND [, ACTION-IF-NOT-FOUND])
-AC_DEFUN(AC_CHECK_CXX_BOOL,
-[AC_MSG_CHECKING([if bool is built-in type])
-AH_TEMPLATE([HAVE_CXX_BOOL], [Define if bool is a built-in type.])
-AC_CACHE_VAL(ac_cv_have_cxx_bool,
-[AC_TRY_COMPILE([],[
-bool b1 = true;
-bool b2 = false;
-],
-eval "ac_cv_have_cxx_bool=yes",
-eval "ac_cv_have_cxx_bool=no")])
-if eval "test \"`echo $ac_cv_have_cxx_bool`\" = yes"; then
-  AC_MSG_RESULT(yes)
-changequote(, )dnl
-  ac_tr_prototype=HAVE_CXX_BOOL
-changequote([, ])dnl
-  AC_DEFINE_UNQUOTED($ac_tr_prototype)
-  ifelse([$1], , :, [$1])
-else
-  AC_MSG_RESULT(no)
-  ifelse([$2], , , [$2])
-fi
-])
-
-
 dnl AC_CHECK_CXX_VOLATILE checks if volatile is a built-in C++ keyword
 dnl   (which is not the case on older compilers).
 
index 4c04502fd5a6600935cc376fe99a250cc3a62e89..9592c9c75cc319f77125825e91fe5a5da66ec15d 100755 (executable)
@@ -1,6 +1,6 @@
 #! /bin/sh
 # Guess values for system-dependent variables and create Makefiles.
-# Generated by GNU Autoconf 2.69 for dcmtk 3.6.5.
+# Generated by GNU Autoconf 2.69 for dcmtk 3.6.6.
 #
 # Report bugs to <bugs@dcmtk.org>.
 #
@@ -579,9 +579,9 @@ MAKEFLAGS=
 
 # Identity of this package.
 PACKAGE_NAME='dcmtk'
-PACKAGE_TARNAME='dcmtk-3.6.5'
-PACKAGE_VERSION='3.6.5'
-PACKAGE_STRING='dcmtk 3.6.5'
+PACKAGE_TARNAME='dcmtk-3.6.6'
+PACKAGE_VERSION='3.6.6'
+PACKAGE_STRING='dcmtk 3.6.6'
 PACKAGE_BUGREPORT='bugs@dcmtk.org'
 PACKAGE_URL='http://www.dcmtk.org/'
 
@@ -696,6 +696,7 @@ infodir
 docdir
 oldincludedir
 includedir
+runstatedir
 localstatedir
 sharedstatedir
 sysconfdir
@@ -811,6 +812,7 @@ datadir='${datarootdir}/dcmtk'
 sysconfdir='${prefix}/etc/dcmtk'
 sharedstatedir='${prefix}/com'
 localstatedir='${prefix}/var'
+runstatedir='${localstatedir}/run'
 includedir='${prefix}/include'
 oldincludedir='/usr/include'
 docdir='${datarootdir}/doc/dcmtk'
@@ -1063,6 +1065,15 @@ do
   | -silent | --silent | --silen | --sile | --sil)
     silent=yes ;;
 
+  -runstatedir | --runstatedir | --runstatedi | --runstated \
+  | --runstate | --runstat | --runsta | --runst | --runs \
+  | --run | --ru | --r)
+    ac_prev=runstatedir ;;
+  -runstatedir=* | --runstatedir=* | --runstatedi=* | --runstated=* \
+  | --runstate=* | --runstat=* | --runsta=* | --runst=* | --runs=* \
+  | --run=* | --ru=* | --r=*)
+    runstatedir=$ac_optarg ;;
+
   -sbindir | --sbindir | --sbindi | --sbind | --sbin | --sbi | --sb)
     ac_prev=sbindir ;;
   -sbindir=* | --sbindir=* | --sbindi=* | --sbind=* | --sbin=* \
@@ -1200,7 +1211,7 @@ fi
 for ac_var in  exec_prefix prefix bindir sbindir libexecdir datarootdir \
                datadir sysconfdir sharedstatedir localstatedir includedir \
                oldincludedir docdir infodir htmldir dvidir pdfdir psdir \
-               libdir localedir mandir
+               libdir localedir mandir runstatedir
 do
   eval ac_val=\$$ac_var
   # Remove trailing slashes.
@@ -1313,7 +1324,7 @@ if test "$ac_init_help" = "long"; then
   # Omit some internal or obsolete options to make the list less imposing.
   # This message is too long to be a string in the A/UX 3.1 sh.
   cat <<_ACEOF
-\`configure' configures dcmtk 3.6.5 to adapt to many kinds of systems.
+\`configure' configures dcmtk 3.6.6 to adapt to many kinds of systems.
 
 Usage: $0 [OPTION]... [VAR=VALUE]...
 
@@ -1353,6 +1364,7 @@ Fine tuning of the installation directories:
   --sysconfdir=DIR        read-only single-machine data [PREFIX/etc/dcmtk]
   --sharedstatedir=DIR    modifiable architecture-independent data [PREFIX/com]
   --localstatedir=DIR     modifiable single-machine data [PREFIX/var]
+  --runstatedir=DIR       modifiable per-process data [LOCALSTATEDIR/run]
   --libdir=DIR            object code libraries [EPREFIX/lib]
   --includedir=DIR        C header files [PREFIX/include]
   --oldincludedir=DIR     C header files for non-gcc [/usr/include]
@@ -1378,7 +1390,7 @@ fi
 
 if test -n "$ac_init_help"; then
   case $ac_init_help in
-     short | recursive ) echo "Configuration of dcmtk 3.6.5:";;
+     short | recursive ) echo "Configuration of dcmtk 3.6.6:";;
    esac
   cat <<\_ACEOF
 
@@ -1551,7 +1563,7 @@ fi
 test -n "$ac_init_help" && exit $ac_status
 if $ac_init_version; then
   cat <<\_ACEOF
-dcmtk configure 3.6.5
+dcmtk configure 3.6.6
 generated by GNU Autoconf 2.69
 
 Copyright (C) 2012 Free Software Foundation, Inc.
@@ -2411,7 +2423,7 @@ cat >config.log <<_ACEOF
 This file contains any messages produced by compilers while
 running configure, to aid debugging if configure makes a mistake.
 
-It was created by dcmtk $as_me 3.6.5, which was
+It was created by dcmtk $as_me 3.6.6, which was
 generated by GNU Autoconf 2.69.  Invocation command line was
 
   $ $0 $@
@@ -2833,9 +2845,10 @@ ac_config_headers="$ac_config_headers include/dcmtk/config/osconfig.h"
 
 
 
-PACKAGE_VERSION_NUMBER=365
+PACKAGE_VERSION_NUMBER=366
 PACKAGE_VERSION_SUFFIX=""
-PACKAGE_DATE="2019-10-28"
+PACKAGE_DATE="2021-01-14"
+
 
 cat >>confdefs.h <<_ACEOF
 #define PACKAGE_VERSION_NUMBER ${PACKAGE_VERSION_NUMBER}
@@ -13061,7 +13074,7 @@ if ${ac_cv_check_std_namespace+:} false; then :
 else
   ac_link_o='${CXX-g++} -o conftest $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.o $LIBS 1>&5'
 cat > conftest.$ac_ext <<EOF
-#line 13064 "configure"
+#line 13076 "configure"
 #include "confdefs.h"
 
 #include <iostream>
@@ -13533,7 +13546,7 @@ if ${ac_cv_check_class_template+:} false; then :
 else
   ac_link_o='${CXX-g++} -o conftest $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.o $LIBS 1>&5'
 cat > conftest.$ac_ext <<EOF
-#line 13536 "configure"
+#line 13548 "configure"
 #include "confdefs.h"
 
 template <class T>
@@ -13605,7 +13618,7 @@ if ${ac_cv_check_static_template_method+:} false; then :
 else
   ac_link_o='${CXX-g++} -o conftest $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.o $LIBS 1>&5'
 cat > conftest.$ac_ext <<EOF
-#line 13608 "configure"
+#line 13620 "configure"
 #include "confdefs.h"
 
 void additive(int & i)
@@ -13677,7 +13690,7 @@ if ${ac_cv_check_function_template+:} false; then :
 else
   ac_link_o='${CXX-g++} -o conftest $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.o $LIBS 1>&5'
 cat > conftest.$ac_ext <<EOF
-#line 13680 "configure"
+#line 13692 "configure"
 #include "confdefs.h"
 
 template <class T>
@@ -13783,49 +13796,6 @@ else
 $as_echo "no" >&6; }
 fi
 
-{ $as_echo "$as_me:${as_lineno-$LINENO}: checking if bool is built-in type" >&5
-$as_echo_n "checking if bool is built-in type... " >&6; }
-
-if ${ac_cv_have_cxx_bool+:} false; then :
-  $as_echo_n "(cached) " >&6
-else
-  cat confdefs.h - <<_ACEOF >conftest.$ac_ext
-/* end confdefs.h.  */
-
-int
-main ()
-{
-
-bool b1 = true;
-bool b2 = false;
-
-  ;
-  return 0;
-}
-_ACEOF
-if ac_fn_cxx_try_compile "$LINENO"; then :
-  eval "ac_cv_have_cxx_bool=yes"
-else
-  eval "ac_cv_have_cxx_bool=no"
-fi
-rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
-fi
-
-if eval "test \"`echo $ac_cv_have_cxx_bool`\" = yes"; then
-  { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
-$as_echo "yes" >&6; }
-  ac_tr_prototype=HAVE_CXX_BOOL
-  cat >>confdefs.h <<_ACEOF
-#define $ac_tr_prototype 1
-_ACEOF
-
-  :
-else
-  { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
-$as_echo "no" >&6; }
-
-fi
-
 { $as_echo "$as_me:${as_lineno-$LINENO}: checking if volatile is known keyword" >&5
 $as_echo_n "checking if volatile is known keyword... " >&6; }
 
@@ -17627,7 +17597,7 @@ cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
 # report actual input values of CONFIG_FILES etc. instead of their
 # values after options handling.
 ac_log="
-This file was extended by dcmtk $as_me 3.6.5, which was
+This file was extended by dcmtk $as_me 3.6.6, which was
 generated by GNU Autoconf 2.69.  Invocation command line was
 
   CONFIG_FILES    = $CONFIG_FILES
@@ -17690,7 +17660,7 @@ _ACEOF
 cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
 ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`"
 ac_cs_version="\\
-dcmtk config.status 3.6.5
+dcmtk config.status 3.6.6
 configured by $0, generated by GNU Autoconf 2.69,
   with options \\"\$ac_cs_config\\"
 
index 3c84bc53770d2037b6aebc3fb8a54c0b57bac957..dfd2321756a63839f3128652a34145f65eab9b2e 100644 (file)
@@ -1,5 +1,5 @@
 dnl Process this file with autoconf to produce a configure script.
-AC_INIT(dcmtk, 3.6.5, [bugs@dcmtk.org], [dcmtk-3.6.5], [http://www.dcmtk.org/])
+AC_INIT(dcmtk, 3.6.6, [bugs@dcmtk.org], [dcmtk-3.6.6], [http://www.dcmtk.org/])
 AC_PREREQ(2.60)
 AC_CONFIG_SRCDIR(Makefile.in)
 AC_CONFIG_HEADERS(include/dcmtk/config/osconfig.h)
@@ -10,9 +10,9 @@ dnl -------------------------------------------------------
 dnl Additional Package Information
 dnl -------------------------------------------------------
 
-PACKAGE_VERSION_NUMBER=365
+PACKAGE_VERSION_NUMBER=366
 PACKAGE_VERSION_SUFFIX=""
-PACKAGE_DATE="2019-10-28"
+PACKAGE_DATE="2021-01-14"
 AC_DEFINE_UNQUOTED(PACKAGE_VERSION_NUMBER,${PACKAGE_VERSION_NUMBER},[Define to the version number of this package.])
 AC_DEFINE_UNQUOTED(PACKAGE_VERSION_SUFFIX,"${PACKAGE_VERSION_SUFFIX}",[Define to the version suffix of this package.])
 AC_DEFINE_UNQUOTED(PACKAGE_DATE,"${PACKAGE_DATE}",[Define to the release date of this package.])
@@ -917,7 +917,6 @@ AC_CHECK_CLASS_TEMPLATE
 AC_CHECK_STATIC_TEMPLATE_METHOD
 AC_CHECK_FUNCTION_TEMPLATE
 AC_CHECK_EXPLICIT_TEMPLATE_SPECIALIZATION
-AC_CHECK_CXX_BOOL
 AC_CHECK_CXX_VOLATILE
 AC_CXX_TYPENAME
 AC_STDIO_NAMESPACE
index b7fff7da28e78eb8b603befe01cf00d26ffb3e06..e36db1802403314c50e4b0075da8324b21e740cd 100755 (executable)
@@ -608,6 +608,7 @@ infodir
 docdir
 oldincludedir
 includedir
+runstatedir
 localstatedir
 sharedstatedir
 sysconfdir
@@ -672,6 +673,7 @@ datadir='${datarootdir}/dcmtk'
 sysconfdir='${prefix}/etc/dcmtk'
 sharedstatedir='${prefix}/com'
 localstatedir='${prefix}/var'
+runstatedir='${localstatedir}/run'
 includedir='${prefix}/include'
 oldincludedir='/usr/include'
 docdir='${datarootdir}/doc/dcmtk'
@@ -924,6 +926,15 @@ do
   | -silent | --silent | --silen | --sile | --sil)
     silent=yes ;;
 
+  -runstatedir | --runstatedir | --runstatedi | --runstated \
+  | --runstate | --runstat | --runsta | --runst | --runs \
+  | --run | --ru | --r)
+    ac_prev=runstatedir ;;
+  -runstatedir=* | --runstatedir=* | --runstatedi=* | --runstated=* \
+  | --runstate=* | --runstat=* | --runsta=* | --runst=* | --runs=* \
+  | --run=* | --ru=* | --r=*)
+    runstatedir=$ac_optarg ;;
+
   -sbindir | --sbindir | --sbindi | --sbind | --sbin | --sbi | --sb)
     ac_prev=sbindir ;;
   -sbindir=* | --sbindir=* | --sbindi=* | --sbind=* | --sbin=* \
@@ -1061,7 +1072,7 @@ fi
 for ac_var in  exec_prefix prefix bindir sbindir libexecdir datarootdir \
                datadir sysconfdir sharedstatedir localstatedir includedir \
                oldincludedir docdir infodir htmldir dvidir pdfdir psdir \
-               libdir localedir mandir
+               libdir localedir mandir runstatedir
 do
   eval ac_val=\$$ac_var
   # Remove trailing slashes.
@@ -1214,6 +1225,7 @@ Fine tuning of the installation directories:
   --sysconfdir=DIR        read-only single-machine data [PREFIX/etc/dcmtk]
   --sharedstatedir=DIR    modifiable architecture-independent data [PREFIX/com]
   --localstatedir=DIR     modifiable single-machine data [PREFIX/var]
+  --runstatedir=DIR       modifiable per-process data [LOCALSTATEDIR/run]
   --libdir=DIR            object code libraries [EPREFIX/lib]
   --includedir=DIR        C header files [PREFIX/include]
   --oldincludedir=DIR     C header files for non-gcc [/usr/include]
index 86c4919371a14547a38261eca0c07bf1b094a5d4..5da0ea2f4e9a9afd58e0a0a8d06cc60d8012f2a1 100644 (file)
@@ -46,6 +46,15 @@ DCMTK_BUILD_IN_PROGRESS
     define this macro yourself since this is done automatically by the build
     system.
 
+DCMTK_UNDEF_SANITIZER
+  Affected: all modules
+  Type of modification: Toolkit customization
+  Explanation: When compiling with the GCC undefined behavior sanitizer
+    (-fsanitize=undefined), this macro must be defined to disable certain code
+    in config/tests/arith.cc that would otherwise trigger a runtime error to be
+    raised by the sanitizer and thus prevent the CMake configure phase from
+    completing.
+
 DCMTK_ENABLE_UNSAFE_VSNPRINTF
   Affected: ofstd
   Type of modification: Activates feature
@@ -191,6 +200,18 @@ ENABLE_BUILTIN_DICTIONARY
     builtin dictionary stays empty.  For further information about dictionary
     configuration read dcmdata/docs/datadict.txt.
 
+ENABLE_DCMJPLS_INTERLEAVE_NONE
+  Affected: dcmjpls
+  Type of modification: Enables feature
+  Explanation: Re-enables the option for uninterleaved encoding
+    (--interleave-none) in the JPEG-LS encoder on command line and library
+    level. This option was removed after DCMTK 3.6.5 since it may in certain
+    cases (color image with BitsStored > 12) create compressed images that
+    are correct but cannot be decoded by the JPEG-LS library due to a known
+    bug (DCMTK issue #892). The option will be re-enabled permanently once
+    DCMTK has been ported to CharLS 2.x, another branch of the JPEG-LS
+    library that requires a C++14 compiler, however.
+
 ENABLE_EXTERNAL_DICTIONARY
   Affected: dcmdata
   Type of modification: Enables feature
@@ -332,6 +353,9 @@ SITE_UID_ROOT
     namespace should compile DCMTK with SITE_UID_ROOT defined to their own
     UID root.  Please make sure that the resulting UIDs do not exceed the
     64 characters limit!
+    DCMTK may add a maximum of 44 characters to the UID root when
+    generating UIDs. Therefore, the root must not be longer than 20
+    characters in order to avoid UID truncation.
 
 STARVIEW
   Affected: dcmimgle, dcmimage
index 006750e1deab57076ca03f201a079c46dc86de23..fcde418dd57813cf17e053dff406f746a3afa0bf 100644 (file)
 /* define if the compiler supports basic C++11 syntax */
 #undef HAVE_CXX11
 
-/* Define if bool is a built-in type. */
-#undef HAVE_CXX_BOOL
-
 /* Define if volatile is a known keyword */
 #undef HAVE_CXX_VOLATILE
 
index 16768209e2ef9223cbbbf937f6ad3175e50e3078..20298ba5e8698e0277f6945101122e7d0456eef4 100644 (file)
@@ -1 +1 @@
-ofstd oflog dcmdata dcmiod dcmfg dcmseg dcmimgle dcmimage dcmjpeg dcmjpls dcmtls dcmnet dcmsr dcmsign dcmwlm dcmqrdb dcmpstat dcmrt dcmtract dcmpmap
+ofstd oflog dcmdata dcmiod dcmfg dcmseg dcmimgle dcmimage dcmjpeg dcmjpls dcmtls dcmnet dcmsr dcmsign dcmwlm dcmqrdb dcmpstat dcmrt dcmtract dcmpmap dcmect
index f3c69db32774ba880d6f644b3be2db8d25af81b3..a61d0e02300074a4a200bc95f630ba3d9286a028 100755 (executable)
@@ -84,7 +84,7 @@ check-nosilent-exhaustive: $makecheckexhaustive
 
 dcmtk-install-doc:
        \$(configdir)/mkinstalldirs \$(DESTDIR)\$(docdir)
-       for file in ANNOUNCE CHANGES COPYRIGHT CREDITS FAQ HISTORY VERSION docs/CHANGES.???; do \\
+       for file in ANNOUNCE COPYRIGHT CREDITS FAQ HISTORY VERSION docs/CHANGES.???; do \\
                \$(INSTALL_DATA) \$\$file \$(DESTDIR)\$(docdir) ;\\
        done
 
index c2cdd9dbafd8219b38788a5ec1140b16ceca4bef..12371170b6d2aa65477b7c552d3e55bfdd435ade 100644 (file)
@@ -189,7 +189,13 @@ static void divide_by_zero()
     //       away or emit compile-time errors.
     volatile T t0 = 1;
     volatile T t1 = 0;
+#ifndef DCMTK_UNDEF_SANITIZER
+    // disable this line when compiling with gcc -fsanitize=undefined
+    // by defining DCMTK_UNDEF_SANITIZER because otherwise this
+    // program will be aborted with a runtime error, thus preventing
+    // CMake from creating the makefiles / project files.
     t0 /= t1;
+#endif
 }
 
 // gathers and prints information for integer types
@@ -353,9 +359,14 @@ static void provoke_snan()
     // we assign a signaling NaN to another float variable
     // and convert it to a quiet NaN.
     volatile T t = guess<T>::snan();
-    // Other compilers will trigger only if we use
-    // arithmetics.
+    // Other compilers will trigger only if we use arithmetics.
+#ifndef DCMTK_UNDEF_SANITIZER
+    // disable this line when compiling with gcc -fsanitize=undefined
+    // by defining DCMTK_UNDEF_SANITIZER because otherwise this
+    // program will be aborted with a runtime error, thus preventing
+    // CMake from creating the makefiles / project files.
     ++t;
+#endif
 }
 
 template<typename T>
index bbb8e752fb614980fe2e48f58ff20af23f6b2f16..273992890bac52d25c0d47d8e6cff2439c86931a 100644 (file)
@@ -1,5 +1,5 @@
 /*
- *  Copyright (C) 2017, OFFIS e.V.
+ *  Copyright (C) 2017-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
index 14d4321dc01834c3735bbfce01ec2679b08d9bc9..db97e15ebd13f18ce744a1b027ca2272aaad3530 100644 (file)
@@ -1,6 +1,6 @@
 /*
 *
-*  Copyright (C) 2016-2017, OFFIS e.V.
+*  Copyright (C) 2016-2020, OFFIS e.V.
 *  All rights reserved.  See COPYRIGHT file for details.
 *
 *  This software and supporting documentation were developed by
@@ -27,6 +27,7 @@
 #include "dcmtk/dcmdata/dcjson.h"
 #include "dcmtk/ofstd/ofstream.h"
 #include "dcmtk/ofstd/ofconapp.h"
+#include "dcmtk/ofstd/ofexit.h"
 
 #ifdef WITH_ZLIB
 #include <zlib.h>                       /* for zlibVersion() */
@@ -38,6 +39,9 @@
 #define OFFIS_CONSOLE_APPLICATION "dcm2json"
 #define OFFIS_CONSOLE_DESCRIPTION "Convert DICOM file and data set to JSON"
 
+#define EXITCODE_CANNOT_CONVERT_TO_UNICODE 80
+#define EXITCODE_CANNOT_WRITE_VALID_JSON   81
+
 static OFLogger dcm2jsonLogger = OFLog::getLogger("dcmtk.apps." OFFIS_CONSOLE_APPLICATION);
 
 static char rcsid[] = "$dcmtk: " OFFIS_CONSOLE_APPLICATION " v"
@@ -51,32 +55,29 @@ static OFCondition writeFile(STD_NAMESPACE ostream &out,
     DcmFileFormat *dfile,
     const E_FileReadMode readMode,
     const OFBool format,
-    const OFBool printMetaInfo)
+    const OFBool printMetaInfo,
+    const OFBool encode_extended)
 {
     OFCondition result = EC_IllegalParameter;
     if ((ifname != NULL) && (dfile != NULL))
     {
-        DcmDataset *dset = dfile->getDataset();
-
         /* write JSON document content */
-
-        if (readMode == ERM_dataset)
+        DcmDataset *dset = dfile->getDataset();
+        if (format)
         {
-            result = format
-            ?
-                dset->writeJson(out, DcmJsonFormatPretty(printMetaInfo))
-            :
-                dset->writeJson(out, DcmJsonFormatCompact(printMetaInfo))
-            ;
+            DcmJsonFormatPretty fmt(printMetaInfo);
+            fmt.setJsonExtensionEnabled(encode_extended);
+            if (readMode == ERM_dataset)
+               result = dset->writeJsonExt(out, fmt, OFTrue, OFTrue);
+               else result = dfile->writeJson(out, fmt);
         }
         else
         {
-            result = format
-            ?
-                dfile->writeJson(out, DcmJsonFormatPretty(printMetaInfo))
-            :
-                dfile->writeJson(out, DcmJsonFormatCompact(printMetaInfo))
-            ;
+            DcmJsonFormatCompact fmt(printMetaInfo);
+            fmt.setJsonExtensionEnabled(encode_extended);
+            if (readMode == ERM_dataset)
+               result = dset->writeJsonExt(out, fmt, OFTrue, OFTrue);
+               else result = dfile->writeJson(out, fmt);
         }
     }
     return result;
@@ -89,7 +90,7 @@ int main(int argc, char *argv[])
 {
     OFBool opt_format = OFTrue;
     OFBool opt_addMetaInformation = OFFalse;
-
+    OFBool opt_encode_extended = OFFalse;
     E_FileReadMode opt_readMode = ERM_autoDetect;
     E_TransferSyntax opt_ixfer = EXS_Unknown;
     OFString optStr;
@@ -119,6 +120,11 @@ int main(int argc, char *argv[])
         cmd.addOption("--read-xfer-big",      "-tb", "read with explicit VR big endian TS");
         cmd.addOption("--read-xfer-implicit", "-ti", "read with implicit VR little endian TS");
 
+    cmd.addGroup("processing options:");
+      cmd.addSubGroup("encoding of infinity and not-a-number:");
+        cmd.addOption("--encode-strict",      "-es", "report error for 'inf' and 'nan' (default)");
+        cmd.addOption("--encode-extended",    "-ee", "permit 'inf' and 'nan' in JSON numbers");
+
     cmd.addGroup("output options:");
       cmd.addSubGroup("output format:");
         cmd.addOption("--formatted-code",     "+fc", "enable whitespace formatting (default)");
@@ -183,6 +189,14 @@ int main(int argc, char *argv[])
         }
         cmd.endOptionBlock();
 
+        /* number encoding options */
+        cmd.beginOptionBlock();
+        if (cmd.findOption("--encode-strict"))
+            opt_encode_extended = OFFalse;
+        if (cmd.findOption("--encode-extended"))
+            opt_encode_extended = OFTrue;
+        cmd.endOptionBlock();
+
         /* format options */
         cmd.beginOptionBlock();
         if (cmd.findOption("--formatted-code"))
@@ -234,11 +248,11 @@ int main(int argc, char *argv[])
                     if (status.bad())
                     {
                         OFLOG_FATAL(dcm2jsonLogger, status.text() << ": converting file to UTF-8: " << ifname);
-                        result = 4;
+                        result = EXITCODE_CANNOT_CONVERT_TO_UNICODE;
                     }
 #else
                     OFLOG_FATAL(dcm2jsonLogger, "character set conversion not available");
-                    return 4;
+                    result = EXITCODE_CANNOT_CONVERT_TO_UNICODE;
 #endif
                 }
             }
@@ -253,25 +267,38 @@ int main(int argc, char *argv[])
                     if (stream.good())
                     {
                         /* write content in JSON format to file */
-                        if (writeFile(stream, ifname, &dfile, opt_readMode, opt_format, opt_addMetaInformation).bad())
-                            result = 2;
+                        status = writeFile(stream, ifname, &dfile, opt_readMode, opt_format, opt_addMetaInformation, opt_encode_extended);
+                        if (status.bad())
+                        {
+                            OFLOG_FATAL(dcm2jsonLogger, status.text() << ": " << ifname);
+                            result = EXITCODE_CANNOT_WRITE_VALID_JSON;
+                        }
                     }
                     else
-                        result = 1;
+                        result = EXITCODE_CANNOT_WRITE_OUTPUT_FILE;
                 }
                 else
                 {
                     /* write content in JSON format to standard output */
-                    if (writeFile(COUT, ifname, &dfile, opt_readMode, opt_format, opt_addMetaInformation).bad())
-                        result = 3;
+                    status = writeFile(COUT, ifname, &dfile, opt_readMode, opt_format, opt_addMetaInformation, opt_encode_extended);
+                    if (status.bad())
+                    {
+                        OFLOG_FATAL(dcm2jsonLogger, status.text() << ": " << ifname);
+                        result = EXITCODE_CANNOT_WRITE_VALID_JSON;
+                    }
                 }
             }
         }
         else
+        {
             OFLOG_ERROR(dcm2jsonLogger, OFFIS_CONSOLE_APPLICATION << ": error (" << status.text() << ") reading file: " << ifname);
+            return EXITCODE_CANNOT_READ_INPUT_FILE;
+        }
     }
     else
+    {
         OFLOG_ERROR(dcm2jsonLogger, OFFIS_CONSOLE_APPLICATION << ": invalid filename: <empty string>");
-
+        return EXITCODE_NO_INPUT_FILES;
+    }
     return result;
 }
index 8acab6610be821856d317225028fcf3107752438..0930cdab025d5567ce0816228a79537a616a122b 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2018, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -84,7 +84,7 @@ int main(int argc, char *argv[])
   const char *opt_ofname = NULL;
 
   E_FileReadMode opt_readMode = ERM_autoDetect;
-  E_FileWriteMode opt_writeMode = EWM_fileformat;
+  E_FileWriteMode opt_writeMode = EWM_createNewMeta;
   E_TransferSyntax opt_ixfer = EXS_Unknown;
   E_TransferSyntax opt_oxfer = EXS_Unknown;
   E_GrpLenEncoding opt_oglenc = EGL_recalcGL;
@@ -189,8 +189,8 @@ int main(int argc, char *argv[])
 
   cmd.addGroup("output options:");
     cmd.addSubGroup("output file format:");
-      cmd.addOption("--write-file",          "+F",     "write file format (default)");
-      cmd.addOption("--write-new-meta-info", "+Fm",    "write file format with new meta information");
+      cmd.addOption("--write-new-meta-info", "+Fm",    "write file format\nwith new meta information (default)");
+      cmd.addOption("--write-file",          "+F",     "write file format");
       cmd.addOption("--write-dataset",       "-F",     "write data set without file meta information");
     cmd.addSubGroup("output transfer syntax:");
       cmd.addOption("--write-xfer-same",     "+t=",    "write with same TS as input (default)");
index a863df7923780da8e9adcb0262119fb5e3be2864..81e6cdf976d64dcf0839ad56a85afa5d6a4ba3fa 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2017, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -15,7 +15,7 @@
  *
  *  Author:  Andreas Barth
  *
- *  Purpose: create a Dicom FileFormat or DataSet from an ASCII-dump
+ *  Purpose: create a DICOM FileFormat or DataSet from an ASCII-dump
  *
  */
 
@@ -34,8 +34,8 @@
  *        two characters.  If the VR can determined from the tag, this part
  *        of a line is optional.
  * Value: There are several rules for writing values:
- *        1. US, SS, SL, UL, FD, FL, OD, OF and OL are written as decimal
- *           strings that can be read by scanf().
+ *        1. US, SS, UL, SL, UV, SV, FD, FL, OD, OF, OL and OV are written as
+ *           decimal strings that can be read by scanf().
  *        2. AT is written as '(gggg,eeee)' with additional spaces stripped
  *           off automatically and gggg and eeee being decimal strings that
  *           can be read by scanf().
@@ -455,6 +455,8 @@ putFileContentsIntoElement(DcmElement *elem, const char *filename)
         ec = EC_IllegalCall;
     if (ec.good())
     {
+        OFLOG_INFO(dump2dcmLogger, "reading " << len << " bytes from binary data file: " << filename);
+        OFLOG_DEBUG(dump2dcmLogger, "  and storing it in the element " << elem->getTag());
         /* read binary file into the buffer */
         if (fread(buf, 1, len, f) != len)
         {
@@ -505,7 +507,7 @@ insertIntoSet(DcmStack &stack, const E_TransferSyntax xfer, const DcmTagKey &tag
            (tagkey != DCM_LUTData || (vr != EVR_US && vr != EVR_SS && vr != EVR_OW)) &&
            (tagkey != DCM_PixelData || (vr != EVR_OB && vr != EVR_OW && vr != EVR_pixelSQ)) &&
            (tagvr != EVR_xs || (vr != EVR_US && vr != EVR_SS)) &&
-           (tagvr != EVR_ox || (vr != EVR_OB && vr != EVR_OW)) &&
+           ((tagvr != EVR_ox && tagvr != EVR_px) || (vr != EVR_OB && vr != EVR_OW)) &&
            (tagvr != EVR_na || vr != EVR_pixelItem))
         {
             OFLOG_WARN(dump2dcmLogger, "Tag " << tag << " with wrong VR '"
index e547b5ead06d3f1961f5c0588927c6a5997ae0da..141e05115a174991661aa9ccd815d7a1c1222394 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2007-2013, OFFIS e.V.
+ *  Copyright (C) 2007-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -188,7 +188,7 @@ static OFCondition startConversion(OFCommandLine& cmd,
   OFCmdUnsignedInt filepad = 0;
   // Item pad length for output DICOM file
   OFCmdUnsignedInt itempad = 0;
-  // Write only pure dataset, i.e. without meta header
+  // Write file format (with meta header)
   E_FileWriteMode writeMode = EWM_fileformat;
   // Override keys are applied at the very end of the conversion "pipeline"
   OFList<OFString> overrideKeys;
index 61187c9a65aae1b2aa67c5bdd3f104e9de08cfb3..e5a6ea1137fa170ed35f27c9a29cb21147ffcbd6 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2003-2017, OFFIS e.V.
+ *  Copyright (C) 2003-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -481,10 +481,10 @@ OFCondition MdfDatasetManager::modifyAllTags(OFString tag_path,
     DcmStack result_stack;
     DcmObject *elem;
     // get references to all matching tags in dataset and store them in stack
-    OFLOG_DEBUG(mdfdsmanLogger, "looking for occurences of: " << key.toString());
+    OFLOG_DEBUG(mdfdsmanLogger, "looking for occurrences of: " << key.toString());
     result=dset->findAndGetElements(key, result_stack);
     // if there are elements found, modify metaheader if necessary
-    OFLOG_DEBUG(mdfdsmanLogger, "found " << result_stack.card() << " occurences");
+    OFLOG_DEBUG(mdfdsmanLogger, "found " << result_stack.card() << " occurrences");
     // as long there are matching elements left on the stack
     while( result_stack.card() > 0 && result.good() )
     {
@@ -652,7 +652,7 @@ OFCondition MdfDatasetManager::saveFile(const char *file_name,
                                  opt_padenc,
                                  OFstatic_cast(Uint32, opt_filepad),
                                  OFstatic_cast(Uint32, opt_itempad),
-                                 (opt_dataset) ? EWM_dataset : EWM_fileformat);
+                                 (opt_dataset) ? EWM_dataset : EWM_createNewMeta);
 
     } else {
         OFLOG_DEBUG(mdfdsmanLogger, "no conversion to transfer syntax " << DcmXfer(opt_xfer).getXferName() << " possible!");
index 6392fb9dfd8f9fd6619de9acbd8d064fae070ff2..2961d5bdad4cc4b851acd26b1d8f7eec11f9d3fc 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2003-2019, OFFIS e.V.
+ *  Copyright (C) 2003-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -224,7 +224,7 @@ static OFCondition createNewElement(xmlNodePtr current,
             if ((tagEVR != dcmEVR) && (dcmEVR != EVR_UNKNOWN) && (tagEVR != EVR_UNKNOWN) &&
                 ((dcmTagKey != DCM_LUTData) || ((dcmEVR != EVR_US) && (dcmEVR != EVR_SS) && (dcmEVR != EVR_OW))) &&
                 ((tagEVR != EVR_xs) || ((dcmEVR != EVR_US) && (dcmEVR != EVR_SS))) &&
-                ((tagEVR != EVR_ox) || ((dcmEVR != EVR_OB) && (dcmEVR != EVR_OW))))
+                (((tagEVR != EVR_ox) && (tagEVR != EVR_px)) || ((dcmEVR != EVR_OB) && (dcmEVR != EVR_OW))))
             {
                 OFLOG_WARN(xml2dcmLogger, "tag " << dcmTag << " has wrong VR (" << dcmVR.getVRName()
                     << "), correct is " << dcmTag.getVR().getVRName());
@@ -309,6 +309,8 @@ static OFCondition putElementContent(xmlNodePtr current,
                         result = element->createUint8Array(OFstatic_cast(Uint32, buflen), buf);
                     if (result.good())
                     {
+                        OFLOG_INFO(xml2dcmLogger, "reading " << fileSize << " bytes from binary data file: " << filename);
+                        OFLOG_DEBUG(xml2dcmLogger, "  and storing it in the element " << element->getTag());
                         /* read binary file into the buffer */
                         if (fread(buf, 1, OFstatic_cast(size_t, fileSize), f) != fileSize)
                         {
@@ -339,6 +341,8 @@ static OFCondition putElementContent(xmlNodePtr current,
                 /* set the value of the newly created element */
                 result = element->putString(OFreinterpret_cast(char *, elemVal));
             }
+            if (result.bad())
+                OFLOG_ERROR(xml2dcmLogger, "cannot put content to element " << element->getTag() << ": " << result.text());
         }
         /* free allocated memory */
         xmlFree(elemVal);
index 66ec3ab829142c1fda64b3053a0a84db17f3357d..4b5cd8610ffb7dd1611d8e154799728e3e16c951 100644 (file)
@@ -5,7 +5,7 @@
 ################################################################################
 # Type 1:  Value MUST be filled in                                             #
 # Type 1C: Value MUST be filled in if known, if certain condition (see         #
-#          standard) is fullfilled, otherwise DO NOT insert                    #
+#          standard) is fulfilled, otherwise DO NOT insert                     #
 # Type 2:  Value MUST be filled in if known, MUST be left empty otherwise      #
 # Type 2C: Same as 2, if a certain condition (see standard) is met. If the     #
 #          condition is not met, DO NOT insert                                 #
index 271ca5363b1d09815d24681963a9bda0b125474f..342dfd8ca2aaf8a1a617c349203c689ff964ec8f 100644 (file)
@@ -5,7 +5,7 @@
 ################################################################################
 # Type 1:  Value MUST be filled in                                             #
 # Type 1C: Value MUST be filled in if known, if certain condition (see         #
-#          standard) is fullfilled, otherwise LEAVE OUT line                   #
+#          standard) is fulfilled, otherwise LEAVE OUT line                    #
 # Type 2:  Value MUST be filled in if known, MUST be left empty otherwise      #
 # Type 2C: Same as 2, if a certain condition (see standard) is met. If the     #
 #          condition is not met, LEAVE OUT line                                #
index cb5c19bc6521873c609b9369a265c7a2089f45d7..698639491d661777081e77fc8c87cc7214eed3ed 100644 (file)
@@ -1,5 +1,5 @@
 #
-#  Copyright (C) 1994-2019, OFFIS e.V.
+#  Copyright (C) 1994-2020, OFFIS e.V.
 #  All rights reserved.  See COPYRIGHT file for details.
 #
 #  This software and supporting documentation were developed by
 # DICONDE (Digital Imaging and Communication in Nondestructive Evaluation) and
 # DICOS (Digital Imaging and Communications in Security) standard.
 #
-# Generated automatically from DICOM PS 3.6-2019b and PS 3.7-2019b
-# File created on 2019-04-26 14:51:35 by J. Riesmeier on thinkpad.
-# File updated manually on 2019-08-07 by J. Riesmeier
+# Generated automatically from DICOM PS 3.6-2020e and PS 3.7-2020e
+# File created on 2020-11-24 14:44:39 by J. Riesmeier on thinkpad.
 #
 # In addition, the data dictionary entries from the following final text
 # supplements and correction items (CP) have been incorporated:
-# - Supplement 175 (FT2)
+# - (none)
 #
 # Each line represents an entry in the data dictionary.  Each line has 5 fields
 # (Tag, VR, Name, VM, Version).  Entries need not be in ascending tag order.
 (0002,0016)    AE      SourceApplicationEntityTitle    1       DICOM
 (0002,0017)    AE      SendingApplicationEntityTitle   1       DICOM
 (0002,0018)    AE      ReceivingApplicationEntityTitle 1       DICOM
+(0002,0026)    UR      SourcePresentationAddress       1       DICOM
+(0002,0027)    UR      SendingPresentationAddress      1       DICOM
+(0002,0028)    UR      ReceivingPresentationAddress    1       DICOM
+(0002,0031)    OB      RTVMetaInformationVersion       1       DICOM
+(0002,0032)    UI      RTVCommunicationSOPClassUID     1       DICOM
+(0002,0033)    UI      RTVCommunicationSOPInstanceUID  1       DICOM
+(0002,0035)    OB      RTVSourceIdentifier     1       DICOM
+(0002,0036)    OB      RTVFlowIdentifier       1       DICOM
+(0002,0037)    UL      RTVFlowRTPSamplingRate  1       DICOM
+(0002,0038)    FD      RTVFlowActualFrameDuration      1       DICOM
 (0002,0100)    UI      PrivateInformationCreatorUID    1       DICOM
 (0002,0102)    OB      PrivateInformation      1       DICOM
 (0004,1130)    CS      FileSetID       1       DICOM
 (0004,1511)    UI      ReferencedSOPInstanceUIDInFile  1       DICOM
 (0004,1512)    UI      ReferencedTransferSyntaxUIDInFile       1       DICOM
 (0004,151A)    UI      ReferencedRelatedGeneralSOPClassUIDInFile       1-n     DICOM
+(0006,0001)    SQ      CurrentFrameFunctionalGroupsSequence    1       DICOM
 (0008,0005)    CS      SpecificCharacterSet    1-n     DICOM
 (0008,0006)    SQ      LanguageCodeSequence    1       DICOM
 (0008,0008)    CS      ImageType       2-n     DICOM
 (0008,2228)    SQ      PrimaryAnatomicStructureSequence        1       DICOM
 (0008,2230)    SQ      PrimaryAnatomicStructureModifierSequence        1       DICOM
 (0008,3001)    SQ      AlternateRepresentationSequence 1       DICOM
+(0008,3002)    UI      AvailableTransferSyntaxUID      1-n     DICOM
 (0008,3010)    UI      IrradiationEventUID     1-n     DICOM
 (0008,3011)    SQ      SourceIrradiationEventSequence  1       DICOM
 (0008,3012)    UI      RadiopharmaceuticalAdministrationEventUID       1       DICOM
 (0016,008C)    OB      GPSAreaInformation      1       DICOM
 (0016,008D)    DT      GPSDateStamp    1       DICOM
 (0016,008E)    IS      GPSDifferential 1       DICOM
+(0016,1001)    CS      LightSourcePolarization 1       DICOM
+(0016,1002)    DS      EmitterColorTemperature 1       DICOM
+(0016,1003)    CS      ContactMethod   1       DICOM
+(0016,1004)    CS      ImmersionMedia  1-n     DICOM
+(0016,1005)    DS      OpticalMagnificationFactor      1       DICOM
 (0018,0010)    LO      ContrastBolusAgent      1       DICOM
 (0018,0012)    SQ      ContrastBolusAgentSequence      1       DICOM
 (0018,0013)    FL      ContrastBolusT1Relaxivity       1       DICOM
 (0018,1008)    LO      GantryID        1       DICOM
 (0018,1009)    UT      UniqueDeviceIdentifier  1       DICOM
 (0018,100A)    SQ      UDISequence     1       DICOM
+(0018,100B)    UI      ManufacturerDeviceClassUID      1-n     DICOM
 (0018,1010)    LO      SecondaryCaptureDeviceID        1       DICOM
 (0018,1012)    DA      DateOfSecondaryCapture  1       DICOM
 (0018,1014)    TM      TimeOfSecondaryCapture  1       DICOM
 (0018,1622)    US      ShutterPresentationValue        1       DICOM
 (0018,1623)    US      ShutterOverlayGroup     1       DICOM
 (0018,1624)    US      ShutterPresentationColorCIELabValue     3       DICOM
+(0018,1630)    CS      OutlineShapeType        1       DICOM
+(0018,1631)    FD      OutlineLeftVerticalEdge 1       DICOM
+(0018,1632)    FD      OutlineRightVerticalEdge        1       DICOM
+(0018,1633)    FD      OutlineUpperHorizontalEdge      1       DICOM
+(0018,1634)    FD      OutlineLowerHorizontalEdge      1       DICOM
+(0018,1635)    FD      CenterOfCircularOutline 2       DICOM
+(0018,1636)    FD      DiameterOfCircularOutline       1       DICOM
+(0018,1637)    UL      NumberOfPolygonalVertices       1       DICOM
+(0018,1638)    OF      VerticesOfThePolygonalOutline   1       DICOM
 (0018,1700)    CS      CollimatorShape 1-3     DICOM
 (0018,1702)    IS      CollimatorLeftVerticalEdge      1       DICOM
 (0018,1704)    IS      CollimatorRightVerticalEdge     1       DICOM
 (0018,3105)    IS      LesionNumber    1-n     DICOM
 (0018,5000)    SH      OutputPower     1-n     DICOM
 (0018,5010)    LO      TransducerData  1-n     DICOM
+(0018,5011)    SQ      TransducerIdentificationSequence        1       DICOM
 (0018,5012)    DS      FocusDepth      1       DICOM
 (0018,5020)    LO      ProcessingFunction      1       DICOM
 (0018,5022)    DS      MechanicalIndex 1       DICOM
 (0032,1066)    UT      ReasonForVisit  1       DICOM
 (0032,1067)    SQ      ReasonForVisitCodeSequence      1       DICOM
 (0032,1070)    LO      RequestedContrastAgent  1       DICOM
+(0034,0001)    SQ      FlowIdentifierSequence  1       DICOM
+(0034,0002)    OB      FlowIdentifier  1       DICOM
+(0034,0003)    UI      FlowTransferSyntaxUID   1       DICOM
+(0034,0004)    UL      FlowRTPSamplingRate     1       DICOM
+(0034,0005)    OB      SourceIdentifier        1       DICOM
+(0034,0007)    OB      FrameOriginTimestamp    1       DICOM
+(0034,0008)    CS      IncludesImagingSubject  1       DICOM
+(0034,0009)    SQ      FrameUsefulnessGroupSequence    1       DICOM
+(0034,000A)    SQ      RealTimeBulkDataFlowSequence    1       DICOM
+(0034,000B)    SQ      CameraPositionGroupSequence     1       DICOM
+(0034,000C)    CS      IncludesInformation     1       DICOM
+(0034,000D)    SQ      TimeOfFrameGroupSequence        1       DICOM
 (0038,0004)    SQ      ReferencedPatientAliasSequence  1       DICOM
 (0038,0008)    CS      VisitStatusID   1       DICOM
 (0038,0010)    LO      AdmissionID     1       DICOM
 (003A,0300)    SQ      MultiplexedAudioChannelsDescriptionCodeSequence 1       DICOM
 (003A,0301)    IS      ChannelIdentificationCode       1       DICOM
 (003A,0302)    CS      ChannelMode     1       DICOM
+(003A,0310)    UI      MultiplexGroupUID       1       DICOM
+(003A,0311)    DS      PowerlineFrequency      1       DICOM
+(003A,0312)    SQ      ChannelImpedanceSequence        1       DICOM
+(003A,0313)    DS      ImpedanceValue  1       DICOM
+(003A,0314)    DT      ImpedanceMeasurementDateTime    1       DICOM
+(003A,0315)    DS      ImpedanceMeasurementFrequency   1       DICOM
+(003A,0316)    CS      ImpedanceMeasurementCurrentType 1       DICOM
 (0040,0001)    AE      ScheduledStationAETitle 1-n     DICOM
 (0040,0002)    DA      ScheduledProcedureStepStartDate 1       DICOM
 (0040,0003)    TM      ScheduledProcedureStepStartTime 1       DICOM
 (0040,A504)    SQ      ContentTemplateSequence 1       DICOM
 (0040,A525)    SQ      IdenticalDocumentsSequence      1       DICOM
 (0040,A730)    SQ      ContentSequence 1       DICOM
+(0040,A801)    SQ      TabulatedValuesSequence 1       DICOM
+(0040,A802)    UL      NumberOfTableRows       1       DICOM
+(0040,A803)    UL      NumbeOfTableColumns     1       DICOM
+(0040,A804)    UL      TableRowNumber  1       DICOM
+(0040,A805)    UL      TableColumnNumber       1       DICOM
+(0040,A806)    SQ      TableRowDefinitionSequence      1       DICOM
+(0040,A807)    SQ      TableColumnDefinitionSequence   1       DICOM
+(0040,A808)    SQ      CellValuesSequence      1       DICOM
 (0040,B020)    SQ      WaveformAnnotationSequence      1       DICOM
 (0040,DB00)    CS      TemplateIdentifier      1       DICOM
 (0040,DB73)    UL      ReferencedContentItemIdentifier 1-n     DICOM
 (0068,7001)    CS      ModelModification       1       DICOM
 (0068,7002)    CS      ModelMirroring  1       DICOM
 (0068,7003)    SQ      ModelUsageCodeSequence  1       DICOM
+(0068,7004)    UI      ModelGroupUID   1       DICOM
+(0068,7005)    UR      RelativeURIReferenceWithinEncapsulatedDocument  1       DICOM
 (0070,0001)    SQ      GraphicAnnotationSequence       1       DICOM
 (0070,0002)    CS      GraphicLayer    1       DICOM
 (0070,0003)    CS      BoundingBoxAnnotationUnits      1       DICOM
 (0072,007E)    SS      SelectorSSValue 1-n     DICOM
 (0072,007F)    UI      SelectorUIValue 1-n     DICOM
 (0072,0080)    SQ      SelectorCodeSequenceValue       1       DICOM
+(0072,0081)    OV      SelectorOVValue 1       DICOM
+(0072,0082)    SV      SelectorSVValue 1-n     DICOM
+(0072,0083)    UV      SelectorUVValue 1-n     DICOM
 (0072,0100)    US      NumberOfScreens 1       DICOM
 (0072,0102)    SQ      NominalScreenDefinitionSequence 1       DICOM
 (0072,0104)    US      NumberOfVerticalPixels  1       DICOM
 (3006,00B8)    FL      ROIElementalCompositionAtomicMassFraction       1       DICOM
 (3006,00C6)    DS      FrameOfReferenceTransformationMatrix    16      DICOM
 (3006,00C8)    LO      FrameOfReferenceTransformationComment   1       DICOM
+(3006,00C9)    SQ      PatientLocationCoordinatesSequence      1       DICOM
+(3006,00CA)    SQ      PatientLocationCoordinatesCodeSequence  1       DICOM
+(3006,00CB)    SQ      PatientSupportPositionSequence  1       DICOM
 (3008,0010)    SQ      MeasuredDoseReferenceSequence   1       DICOM
 (3008,0012)    ST      MeasuredDoseDescription 1       DICOM
 (3008,0014)    CS      MeasuredDoseType        1       DICOM
 (300A,007A)    IS      RepeatFractionCycleLength       1       DICOM
 (300A,007B)    LT      FractionPattern 1       DICOM
 (300A,0080)    IS      NumberOfBeams   1       DICOM
-(300A,0082)    DS      BeamDoseSpecificationPoint      3       DICOM
 (300A,0083)    UI      ReferencedDoseReferenceUID      1       DICOM
 (300A,0084)    DS      BeamDose        1       DICOM
 (300A,0086)    DS      BeamMeterset    1       DICOM
 (300A,0395)    CS      ScanSpotReorderingAllowed       1       DICOM
 (300A,0396)    FL      ScanSpotMetersetWeights 1-n     DICOM
 (300A,0398)    FL      ScanningSpotSize        2       DICOM
+(300A,0399)    FL      ScanSpotSizesDelivered  2-2n    DICOM
 (300A,039A)    IS      NumberOfPaintings       1       DICOM
 (300A,03A0)    SQ      IonToleranceTableSequence       1       DICOM
 (300A,03A2)    SQ      IonBeamSequence 1       DICOM
 (300A,0423)    CS      GeneralAccessoryType    1       DICOM
 (300A,0424)    IS      GeneralAccessoryNumber  1       DICOM
 (300A,0425)    FL      SourceToGeneralAccessoryDistance        1       DICOM
+(300A,0426)    DS      IsocenterToGeneralAccessoryDistance     1       DICOM
 (300A,0431)    SQ      ApplicatorGeometrySequence      1       DICOM
 (300A,0432)    CS      ApplicatorApertureShape 1       DICOM
 (300A,0433)    FL      ApplicatorOpening       1       DICOM
 (300A,0510)    FL      DeliveredNominalRangeModulatedRegionDepths      2       DICOM
 (300A,0511)    CS      DeliveredReferenceDoseDefinition        1       DICOM
 (300A,0512)    CS      ReferenceDoseDefinition 1       DICOM
+(300A,0600)    US      RTControlPointIndex     1       DICOM
+(300A,0601)    US      RadiationGenerationModeIndex    1       DICOM
+(300A,0602)    US      ReferencedDefinedDeviceIndex    1       DICOM
+(300A,0603)    US      RadiationDoseIdentificationIndex        1       DICOM
+(300A,0604)    US      NumberOfRTControlPoints 1       DICOM
+(300A,0605)    US      ReferencedRadiationGenerationModeIndex  1       DICOM
+(300A,0606)    US      TreatmentPositionIndex  1       DICOM
+(300A,0607)    US      ReferencedDeviceIndex   1       DICOM
+(300A,0608)    LO      TreatmentPositionGroupLabel     1       DICOM
+(300A,0609)    UI      TreatmentPositionGroupUID       1       DICOM
+(300A,060A)    SQ      TreatmentPositionGroupSequence  1       DICOM
+(300A,060B)    US      ReferencedTreatmentPositionIndex        1       DICOM
+(300A,060C)    US      ReferencedRadiationDoseIdentificationIndex      1       DICOM
+(300A,060D)    FD      RTAccessoryHolderWaterEquivalentThickness       1       DICOM
+(300A,060E)    US      ReferencedRTAccessoryHolderDeviceIndex  1       DICOM
+(300A,060F)    CS      RTAccessoryHolderSlotExistenceFlag      1       DICOM
+(300A,0610)    SQ      RTAccessoryHolderSlotSequence   1       DICOM
+(300A,0611)    LO      RTAccessoryHolderSlotID 1       DICOM
+(300A,0612)    FD      RTAccessoryHolderSlotDistance   1       DICOM
+(300A,0613)    FD      RTAccessorySlotDistance 1       DICOM
+(300A,0614)    SQ      RTAccessoryHolderDefinitionSequence     1       DICOM
+(300A,0615)    LO      RTAccessoryDeviceSlotID 1       DICOM
+(300A,0616)    SQ      RTRadiationSequence     1       DICOM
+(300A,0617)    SQ      RadiationDoseSequence   1       DICOM
+(300A,0618)    SQ      RadiationDoseIdentificationSequence     1       DICOM
+(300A,0619)    LO      RadiationDoseIdentificationLabel        1       DICOM
+(300A,061A)    CS      ReferenceDoseType       1       DICOM
+(300A,061B)    CS      PrimaryDoseValueIndicator       1       DICOM
+(300A,061C)    SQ      DoseValuesSequence      1       DICOM
+(300A,061D)    CS      DoseValuePurpose        1-n     DICOM
+(300A,061E)    FD      ReferenceDosePointCoordinates   3       DICOM
+(300A,061F)    SQ      RadiationDoseValuesParametersSequence   1       DICOM
+(300A,0620)    SQ      MetersetToDoseMappingSequence   1       DICOM
+(300A,0621)    SQ      ExpectedInVivoMeasurementValuesSequence 1       DICOM
+(300A,0622)    US      ExpectedInVivoMeasurementValueIndex     1       DICOM
+(300A,0623)    LO      RadiationDoseInVivoMeasurementLabel     1       DICOM
+(300A,0624)    FD      RadiationDoseCentralAxisDisplacement    2       DICOM
+(300A,0625)    FD      RadiationDoseValue      1       DICOM
+(300A,0626)    FD      RadiationDoseSourceToSkinDistance       1       DICOM
+(300A,0627)    FD      RadiationDoseMeasurementPointCoordinates        3       DICOM
+(300A,0628)    FD      RadiationDoseSourceToExternalContourDistance    1       DICOM
+(300A,0629)    SQ      RTToleranceSetSequence  1       DICOM
+(300A,062A)    LO      RTToleranceSetLabel     1       DICOM
+(300A,062B)    SQ      AttributeToleranceValuesSequence        1       DICOM
+(300A,062C)    FD      ToleranceValue  1       DICOM
+(300A,062D)    SQ      PatientSupportPositionToleranceSequence 1       DICOM
+(300A,062E)    FD      TreatmentTimeLimit      1       DICOM
+(300A,062F)    SQ      CArmPhotonElectronControlPointSequence  1       DICOM
+(300A,0630)    SQ      ReferencedRTRadiationSequence   1       DICOM
+(300A,0631)    SQ      ReferencedRTInstanceSequence    1       DICOM
+(300A,0632)    SQ      ReferencedRTPatientSetupSequence        1       DICOM
+(300A,0634)    FD      SourceToPatientSurfaceDistance  1       DICOM
+(300A,0635)    SQ      TreatmentMachineSpecialModeCodeSequence 1       DICOM
+(300A,0636)    US      IntendedNumberOfFractions       1       DICOM
+(300A,0637)    CS      RTRadiationSetIntent    1       DICOM
+(300A,0638)    CS      RTRadiationPhysicalAndGeometricContentDetailFlag        1       DICOM
+(300A,0639)    CS      RTRecordFlag    1       DICOM
+(300A,063A)    SQ      TreatmentDeviceIdentificationSequence   1       DICOM
+(300A,063B)    SQ      ReferencedRTPhysicianIntentSequence     1       DICOM
+(300A,063C)    FD      CumulativeMeterset      1       DICOM
+(300A,063D)    FD      DeliveryRate    1       DICOM
+(300A,063E)    SQ      DeliveryRateUnitSequence        1       DICOM
+(300A,063F)    SQ      TreatmentPositionSequence       1       DICOM
+(300A,0640)    FD      RadiationSourceAxisDistance     1       DICOM
+(300A,0641)    US      NumberOfRTBeamLimitingDevices   1       DICOM
+(300A,0642)    FD      RTBeamLimitingDeviceProximalDistance    1       DICOM
+(300A,0643)    FD      RTBeamLimitingDeviceDistalDistance      1       DICOM
+(300A,0644)    SQ      ParallelRTBeamDelimiterDeviceOrientationLabelCodeSequence       1       DICOM
+(300A,0645)    FD      BeamModifierOrientationAngle    1       DICOM
+(300A,0646)    SQ      FixedRTBeamDelimiterDeviceSequence      1       DICOM
+(300A,0647)    SQ      ParallelRTBeamDelimiterDeviceSequence   1       DICOM
+(300A,0648)    US      NumberOfParallelRTBeamDelimiters        1       DICOM
+(300A,0649)    FD      ParallelRTBeamDelimiterBoundaries       2-n     DICOM
+(300A,064A)    FD      ParallelRTBeamDelimiterPositions        2-n     DICOM
+(300A,064B)    FD      RTBeamLimitingDeviceOffset      2       DICOM
+(300A,064C)    SQ      RTBeamDelimiterGeometrySequence 1       DICOM
+(300A,064D)    SQ      RTBeamLimitingDeviceDefinitionSequence  1       DICOM
+(300A,064E)    CS      ParallelRTBeamDelimiterOpeningMode      1       DICOM
+(300A,064F)    CS      ParallelRTBeamDelimiterLeafMountingSide 1-n     DICOM
+(300A,0650)    UI      PatientSetupUID 1       DICOM
+(300A,0651)    SQ      WedgeDefinitionSequence 1       DICOM
+(300A,0652)    FD      RadiationBeamWedgeAngle 1       DICOM
+(300A,0653)    FD      RadiationBeamWedgeThinEdgeDistance      1       DICOM
+(300A,0654)    FD      RadiationBeamEffectiveWedgeAngle        1       DICOM
+(300A,0655)    US      NumberOfWedgePositions  1       DICOM
+(300A,0656)    SQ      RTBeamLimitingDeviceOpeningSequence     1       DICOM
+(300A,0657)    US      NumberOfRTBeamLimitingDeviceOpenings    1       DICOM
+(300A,0658)    SQ      RadiationDosimeterUnitSequence  1       DICOM
+(300A,0659)    SQ      RTDeviceDistanceReferenceLocationCodeSequence   1       DICOM
+(300A,065A)    SQ      RadiationDeviceConfigurationAndCommissioningKeySequence 1       DICOM
+(300A,065B)    SQ      PatientSupportPositionParameterSequence 1       DICOM
+(300A,065C)    CS      PatientSupportPositionSpecificationMethod       1       DICOM
+(300A,065D)    SQ      PatientSupportPositionDeviceParameterSequence   1       DICOM
+(300A,065E)    US      DeviceOrderIndex        1       DICOM
+(300A,065F)    US      PatientSupportPositionParameterOrderIndex       1       DICOM
+(300A,0660)    SQ      PatientSupportPositionDeviceToleranceSequence   1       DICOM
+(300A,0661)    US      PatientSupportPositionToleranceOrderIndex       1       DICOM
+(300A,0662)    SQ      CompensatorDefinitionSequence   1       DICOM
+(300A,0663)    CS      CompensatorMapOrientation       1       DICOM
+(300A,0664)    OF      CompensatorProximalThicknessMap 1       DICOM
+(300A,0665)    OF      CompensatorDistalThicknessMap   1       DICOM
+(300A,0666)    FD      CompensatorBasePlaneOffset      1       DICOM
+(300A,0667)    SQ      CompensatorShapeFabricationCodeSequence 1       DICOM
+(300A,0668)    SQ      CompensatorShapeSequence        1       DICOM
+(300A,0669)    FD      RadiationBeamCompensatorMillingToolDiameter     1       DICOM
+(300A,066A)    SQ      BlockDefinitionSequence 1       DICOM
+(300A,066B)    OF      BlockEdgeData   1       DICOM
+(300A,066C)    CS      BlockOrientation        1       DICOM
+(300A,066D)    FD      RadiationBeamBlockThickness     1       DICOM
+(300A,066E)    FD      RadiationBeamBlockSlabThickness 1       DICOM
+(300A,066F)    SQ      BlockEdgeDataSequence   1       DICOM
+(300A,0670)    US      NumberOfRTAccessoryHolders      1       DICOM
+(300A,0671)    SQ      GeneralAccessoryDefinitionSequence      1       DICOM
+(300A,0672)    US      NumberOfGeneralAccessories      1       DICOM
+(300A,0673)    SQ      BolusDefinitionSequence 1       DICOM
+(300A,0674)    US      NumberOfBoluses 1       DICOM
+(300A,0675)    UI      EquipmentFrameOfReferenceUID    1       DICOM
+(300A,0676)    ST      EquipmentFrameOfReferenceDescription    1       DICOM
+(300A,0677)    SQ      EquipmentReferencePointCoordinatesSequence      1       DICOM
+(300A,0678)    SQ      EquipmentReferencePointCodeSequence     1       DICOM
+(300A,0679)    FD      RTBeamLimitingDeviceAngle       1       DICOM
+(300A,067A)    FD      SourceRollAngle 1       DICOM
+(300A,067B)    SQ      RadiationGenerationModeSequence 1       DICOM
+(300A,067C)    SH      RadiationGenerationModeLabel    1       DICOM
+(300A,067D)    ST      RadiationGenerationModeDescription      1       DICOM
+(300A,067E)    SQ      RadiationGenerationModeMachineCodeSequence      1       DICOM
+(300A,067F)    SQ      RadiationTypeCodeSequence       1       DICOM
+(300A,0680)    DS      NominalEnergy   1       DICOM
+(300A,0681)    DS      MinimumNominalEnergy    1       DICOM
+(300A,0682)    DS      MaximumNominalEnergy    1       DICOM
+(300A,0683)    SQ      RadiationFluenceModifierCodeSequence    1       DICOM
+(300A,0684)    SQ      EnergyUnitCodeSequence  1       DICOM
+(300A,0685)    US      NumberOfRadiationGenerationModes        1       DICOM
+(300A,0686)    SQ      PatientSupportDevicesSequence   1       DICOM
+(300A,0687)    US      NumberOfPatientSupportDevices   1       DICOM
+(300A,0688)    FD      RTBeamModifierDefinitionDistance        1       DICOM
+(300A,0689)    SQ      BeamAreaLimitSequence   1       DICOM
+(300A,068A)    SQ      ReferencedRTPrescriptionSequence        1       DICOM
+(300A,0700)    UI      TreatmentSessionUID     1       DICOM
+(300A,0701)    CS      RTRadiationUsage        1       DICOM
+(300A,0702)    SQ      ReferencedRTRadiationSetSequence        1       DICOM
+(300A,0703)    SQ      ReferencedRTRadiationRecordSequence     1       DICOM
+(300A,0704)    US      RTRadiationSetDeliveryNumber    1       DICOM
+(300A,0705)    US      ClinicalFractionNumber  1       DICOM
+(300A,0706)    CS      RTTreatmentFractionCompletionStatus     1       DICOM
+(300A,0707)    CS      RTRadiationSetUsage     1       DICOM
+(300A,0708)    CS      TreatmentDeliveryContinuationFlag       1       DICOM
+(300A,0709)    CS      TreatmentRecordContentOrigin    1       DICOM
+(300A,0714)    CS      RTTreatmentTerminationStatus    1       DICOM
+(300A,0715)    SQ      RTTreatmentTerminationReasonCodeSequence        1       DICOM
+(300A,0716)    SQ      MachineSpecificTreatmentTerminationCodeSequence 1       DICOM
+(300A,0722)    SQ      RTRadiationSalvageRecordControlPointSequence    1       DICOM
+(300A,0723)    CS      StartingMetersetValueKnownFlag  1       DICOM
+(300A,0730)    ST      TreatmentTerminationDescription 1       DICOM
+(300A,0731)    SQ      TreatmentToleranceViolationSequence     1       DICOM
+(300A,0732)    CS      TreatmentToleranceViolationCategory     1       DICOM
+(300A,0733)    SQ      TreatmentToleranceViolationAttributeSequence    1       DICOM
+(300A,0734)    ST      TreatmentToleranceViolationDescription  1       DICOM
+(300A,0735)    ST      TreatmentToleranceViolationIdentification       1       DICOM
+(300A,0736)    DT      TreatmentToleranceViolationDateTime     1       DICOM
+(300A,073A)    DT      RecordedRTControlPointDateTime  1       DICOM
+(300A,073B)    US      ReferencedRadiationRTControlPointIndex  1       DICOM
+(300A,073E)    SQ      AlternateValueSequence  1       DICOM
+(300A,073F)    SQ      ConfirmationSequence    1       DICOM
+(300A,0740)    SQ      InterlockSequence       1       DICOM
+(300A,0741)    DT      InterlockDateTime       1       DICOM
+(300A,0742)    ST      InterlockDescription    1       DICOM
+(300A,0743)    SQ      InterlockOriginatingDeviceSequence      1       DICOM
+(300A,0744)    SQ      InterlockCodeSequence   1       DICOM
+(300A,0745)    SQ      InterlockResolutionCodeSequence 1       DICOM
+(300A,0746)    SQ      InterlockResolutionUserSequence 1       DICOM
+(300A,0760)    DT      OverrideDateTime        1       DICOM
+(300A,0761)    SQ      TreatmentToleranceViolationTypeCodeSequence     1       DICOM
+(300A,0762)    SQ      TreatmentToleranceViolationCauseCodeSequence    1       DICOM
+(300A,0772)    SQ      MeasuredMetersetToDoseMappingSequence   1       DICOM
+(300A,0773)    US      ReferencedExpectedInVivoMeasurementValueIndex   1       DICOM
+(300A,0774)    SQ      DoseMeasurementDeviceCodeSequence       1       DICOM
+(300A,0780)    SQ      AdditionalParameterRecordingInstanceSequence    1       DICOM
+(300A,0783)    ST      InterlockOriginDescription      1       DICOM
 (300C,0002)    SQ      ReferencedRTPlanSequence        1       DICOM
 (300C,0004)    SQ      ReferencedBeamSequence  1       DICOM
 (300C,0006)    IS      ReferencedBeamNumber    1       DICOM
 (3010,002C)    SQ      SegmentAnnotationTypeCodeSequence       1       DICOM
 (3010,002D)    LO      DeviceLabel     1       DICOM
 (3010,002E)    SQ      DeviceTypeCodeSequence  1       DICOM
+(3010,002F)    SQ      SegmentAnnotationTypeModifierCodeSequence       1       DICOM
 (3010,0030)    SQ      PatientEquipmentRelationshipCodeSequence        1       DICOM
 (3010,0031)    UI      ReferencedFiducialsUID  1       DICOM
 (3010,0032)    SQ      PatientTreatmentOrientationSequence     1       DICOM
 (3010,0086)    LT      IntendedStartDayOfWeek  1       DICOM
 (3010,0087)    SQ      WeekdayFractionPatternSequence  1       DICOM
 (3010,0088)    SQ      DeliveryTimeStructureCodeSequence       1       DICOM
+(3010,0089)    SQ      TreatmentSiteModifierCodeSequence       1       DICOM
+(3010,0090)    CS      RoboticBaseLocationIndicator    1       DICOM
+(3010,0091)    SQ      RoboticPathNodeSetCodeSequence  1       DICOM
+(3010,0092)    UL      RoboticNodeIdentifier   1       DICOM
+(3010,0093)    FD      RTTreatmentSourceCoordinates    3       DICOM
+(3010,0094)    FD      RadiationSourceCoordinateSystemYawAngle 1       DICOM
+(3010,0095)    FD      RadiationSourceCoordinateSystemRollAngle        1       DICOM
+(3010,0096)    FD      RadiationSourceCoordinateSystemPitchAngle       1       DICOM
+(3010,0097)    SQ      RoboticPathControlPointSequence 1       DICOM
+(3010,0098)    SQ      TomotherapeuticControlPointSequence     1       DICOM
+(3010,0099)    FD      TomotherapeuticLeafOpenDurations        1-n     DICOM
+(3010,009A)    FD      TomotherapeuticLeafInitialClosedDurations       1-n     DICOM
 (4010,0001)    CS      LowEnergyDetectors      1       DICOM/DICOS
 (4010,0002)    CS      HighEnergyDetectors     1       DICOM/DICOS
 (4010,0004)    SQ      DetectorGeometrySequence        1       DICOM/DICOS
 (4010,1026)    DT      RouteSegmentEndTime     1       DICOM/DICOS
 (4010,1027)    CS      TDRType 1       DICOM/DICOS
 (4010,1028)    CS      InternationalRouteSegment       1       DICOM/DICOS
-(4010,1029)    LO      ThreatDetectionAlgorithmandVersion      1-n     DICOM/DICOS
+(4010,1029)    LO      ThreatDetectionAlgorithmAndVersion      1-n     DICOM/DICOS
 (4010,102A)    SH      AssignedLocation        1       DICOM/DICOS
 (4010,102B)    DT      AlarmDecisionTime       1       DICOM/DICOS
 (4010,1031)    CS      AlarmDecision   1       DICOM/DICOS
 (7FE0,0002)    OV      ExtendedOffsetTableLengths      1       DICOM
 (7FE0,0008)    OF      FloatPixelData  1       DICOM
 (7FE0,0009)    OD      DoubleFloatPixelData    1       DICOM
-(7FE0,0010)    ox      PixelData       1       DICOM
+(7FE0,0010)    px      PixelData       1       DICOM
 (FFFA,FFFA)    SQ      DigitalSignaturesSequence       1       DICOM
 (FFFC,FFFC)    OB      DataSetTrailingPadding  1       DICOM
 (FFFE,E000)    na      Item    1       DICOM
 (3006,00C0)    SQ      RETIRED_FrameOfReferenceRelationshipSequence    1       DICOM/retired
 (3006,00C2)    UI      RETIRED_RelatedFrameOfReferenceUID      1       DICOM/retired
 (3006,00C4)    CS      RETIRED_FrameOfReferenceTransformationType      1       DICOM/retired
+(300A,0082)    DS      RETIRED_BeamDoseSpecificationPoint      3       DICOM/retired
 (300A,008D)    FL      RETIRED_AverageBeamDosePointDepth       1       DICOM/retired
 (300A,008E)    FL      RETIRED_AverageBeamDosePointEquivalentDepth     1       DICOM/retired
 (300A,008F)    FL      RETIRED_AverageBeamDosePointSSD 1       DICOM/retired
 #
 #---------------------------------------------------------------------------
 #
-# Supplement 175 (Second Generation Radiotherapy - C-Arm RT Treatment Modalities)
-#
-(0018,100B)    UI      ManufacturerDeviceClassUID      1-n     DICOM/Supplement_175
-(0018,1630)    CS      OutlineShapeType        1       DICOM/Supplement_175
-(0018,1631)    FD      OutlineLeftVerticalEdge 1       DICOM/Supplement_175
-(0018,1632)    FD      OutlineRightVerticalEdge        1       DICOM/Supplement_175
-(0018,1633)    FD      OutlineUpperHorizontalEdge      1       DICOM/Supplement_175
-(0018,1634)    FD      OutlineLowerHorizontalEdge      1       DICOM/Supplement_175
-(0018,1635)    FD      CenterOfCircularOutline 2       DICOM/Supplement_175
-(0018,1636)    FD      DiameterOfCircularOutline       1       DICOM/Supplement_175
-(0018,1637)    UL      NumberOfPolygonalVertices       1       DICOM/Supplement_175
-(0018,1638)    OF      VerticesOfThePolygonalOutline   1       DICOM/Supplement_175
-(3006,00C9)    SQ      PatientLocationCoordinatesSequence      1       DICOM/Supplement_175
-(3006,00CA)    SQ      PatientLocationCoordinatesCodeSequence  1       DICOM/Supplement_175
-(3006,00CB)    SQ      PatientSupportPositionSequence  1       DICOM/Supplement_175
-(300A,0600)    US      RTControlPointIndex     1       DICOM/Supplement_175
-(300A,0601)    US      RadiationGenerationModeIndex    1       DICOM/Supplement_175
-(300A,0602)    US      ReferencedDefinedDeviceIndex    1       DICOM/Supplement_175
-(300A,0603)    US      RadiationDoseIdentificationIndex        1       DICOM/Supplement_175
-(300A,0604)    US      NumberOfRTControlPoints 1       DICOM/Supplement_175
-(300A,0605)    US      ReferencedRadiationGenerationModeIndex  1       DICOM/Supplement_175
-(300A,0606)    US      TreatmentPositionIndex  1       DICOM/Supplement_175
-(300A,0607)    US      ReferencedDeviceIndex   1       DICOM/Supplement_175
-(300A,0608)    LO      TreatmentPositionGroupLabel     1       DICOM/Supplement_175
-(300A,0609)    UI      TreatmentPositionGroupUID       1       DICOM/Supplement_175
-(300A,060A)    SQ      TreatmentPositionGroupSequence  1       DICOM/Supplement_175
-(300A,060B)    US      ReferencedTreatmentPositionIndex        1       DICOM/Supplement_175
-(300A,060C)    US      ReferencedRadiationDoseIdentificationIndex      1       DICOM/Supplement_175
-(300A,060D)    FD      RTAccessoryHolderWaterEquivalentThickness       1       DICOM/Supplement_175
-(300A,060E)    US      ReferencedRTAccessoryHolderDeviceIndex  1       DICOM/Supplement_175
-(300A,060F)    CS      RTAccessoryHolderSlotExistenceFlag      1       DICOM/Supplement_175
-(300A,0610)    SQ      RTAccessoryHolderSlotSequence   1       DICOM/Supplement_175
-(300A,0611)    LO      RTAccessoryHolderSlotID 1       DICOM/Supplement_175
-(300A,0612)    FD      RTAccessoryHolderSlotDistance   1       DICOM/Supplement_175
-(300A,0613)    FD      RTAccessorySlotDistance 1       DICOM/Supplement_175
-(300A,0614)    SQ      RTAccessoryHolderDefinitionSequence     1       DICOM/Supplement_175
-(300A,0615)    LO      RTAccessoryDeviceSlotID 1       DICOM/Supplement_175
-(300A,0616)    SQ      RTRadiationSequence     1       DICOM/Supplement_175
-(300A,0617)    SQ      RadiationDoseSequence   1       DICOM/Supplement_175
-(300A,0618)    SQ      RadiationDoseIdentificationSequence     1       DICOM/Supplement_175
-(300A,0619)    LO      RadiationDoseIdentificationLabel        1       DICOM/Supplement_175
-(300A,061A)    CS      ReferenceDoseType       1       DICOM/Supplement_175
-(300A,061B)    CS      PrimaryDoseValueIndicator       1       DICOM/Supplement_175
-(300A,061C)    SQ      DoseValuesSequence      1       DICOM/Supplement_175
-(300A,061D)    CS      DoseValuePurpose        1-n     DICOM/Supplement_175
-(300A,061E)    FD      ReferenceDosePointCoordinates   3       DICOM/Supplement_175
-(300A,061F)    SQ      RadiationDoseValuesParametersSequence   1       DICOM/Supplement_175
-(300A,0620)    SQ      MetersetToDoseMappingSequence   1       DICOM/Supplement_175
-(300A,0621)    SQ      ExpectedInVivoMeasurementValuesSequence 1       DICOM/Supplement_175
-(300A,0622)    US      ExpectedInVivoMeasurementValueIndex     1       DICOM/Supplement_175
-(300A,0623)    LO      RadiationDoseInVivoMeasurementLabel     1       DICOM/Supplement_175
-(300A,0624)    FD      RadiationDoseCentralAxisDisplacement    2       DICOM/Supplement_175
-(300A,0625)    FD      RadiationDoseValue      1       DICOM/Supplement_175
-(300A,0626)    FD      RadiationDoseSourceToSkinDistance       1       DICOM/Supplement_175
-(300A,0627)    FD      RadiationDoseMeasurementPointCoordinates        3       DICOM/Supplement_175
-(300A,0628)    FD      RadiationDoseSourceToExternalContourDistance    1       DICOM/Supplement_175
-(300A,0629)    SQ      RTToleranceSetSequence  1       DICOM/Supplement_175
-(300A,062A)    LO      RTToleranceSetLabel     1       DICOM/Supplement_175
-(300A,062B)    SQ      AttributeToleranceValuesSequence        1       DICOM/Supplement_175
-(300A,062C)    FD      ToleranceValue  1       DICOM/Supplement_175
-(300A,062D)    SQ      PatientSupportPositionToleranceSequence 1       DICOM/Supplement_175
-(300A,062E)    FD      TreatmentTimeLimit      1       DICOM/Supplement_175
-(300A,062F)    SQ      CArmPhotonElectronControlPointSequence  1       DICOM/Supplement_175
-(300A,0630)    SQ      ReferencedRTRadiationSequence   1       DICOM/Supplement_175
-(300A,0631)    SQ      ReferencedRTInstanceSequence    1       DICOM/Supplement_175
-(300A,0632)    SQ      ReferencedRTPatientSetupSequence        1       DICOM/Supplement_175
-(300A,0634)    FD      SourceToPatientSurfaceDistance  1       DICOM/Supplement_175
-(300A,0635)    SQ      TreatmentMachineSpecialModeCodeSequence 1       DICOM/Supplement_175
-(300A,0636)    US      IntendedNumberOfFractions       1       DICOM/Supplement_175
-(300A,0637)    CS      RTRadiationSetIntent    1       DICOM/Supplement_175
-(300A,0638)    CS      RTRadiationPhysicalAndGeometricContentDetailFlag        1       DICOM/Supplement_175
-(300A,0639)    CS      RTRecordFlag    1       DICOM/Supplement_175
-(300A,063A)    SQ      TreatmentDeviceIdentificationSequence   1       DICOM/Supplement_175
-(300A,063B)    SQ      ReferencedRTPhysicianIntentSequence     1       DICOM/Supplement_175
-(300A,063C)    FD      CumulativeMeterset      1       DICOM/Supplement_175
-(300A,063D)    FD      DeliveryRate    1       DICOM/Supplement_175
-(300A,063E)    SQ      DeliveryRateUnitSequence        1       DICOM/Supplement_175
-(300A,063F)    SQ      TreatmentPositionSequence       1       DICOM/Supplement_175
-(300A,0640)    FD      RadiationSourceAxisDistance     1       DICOM/Supplement_175
-(300A,0641)    US      NumberOfRTBeamLimitingDevices   1       DICOM/Supplement_175
-(300A,0642)    FD      RTBeamLimitingDeviceProximalDistance    1       DICOM/Supplement_175
-(300A,0643)    FD      RTBeamLimitingDeviceDistalDistance      1       DICOM/Supplement_175
-(300A,0644)    SQ      ParallelRTBeamDelimiterDeviceOrientationLabelCodeSequence       1       DICOM/Supplement_175
-(300A,0645)    FD      BeamsModifierOrientationAngle   1       DICOM/Supplement_175
-(300A,0646)    SQ      FixedRTBeamDelimiterDeviceSequence      1       DICOM/Supplement_175
-(300A,0647)    SQ      ParallelRTBeamDelimiterDeviceSequence   1       DICOM/Supplement_175
-(300A,0648)    US      NumberOfParallelRTBeamDelimiters        1       DICOM/Supplement_175
-(300A,0649)    FD      ParallelRTBeamDelimiterBoundaries       2-n     DICOM/Supplement_175
-(300A,064A)    FD      ParallelRTBeamDelimiterPositions        2-n     DICOM/Supplement_175
-(300A,064B)    FD      RTBeamLimitingDeviceOffset      2       DICOM/Supplement_175
-(300A,064C)    SQ      RTBeamDelimiterGeometrySequence 1       DICOM/Supplement_175
-(300A,064D)    SQ      RTBeamLimitingDeviceDefinitionSequence  1       DICOM/Supplement_175
-(300A,064E)    CS      ParallelRTBeamDelimiterOpeningMode      1       DICOM/Supplement_175
-(300A,064F)    CS      ParallelRTBeamDelimiterLeafMountingSide 1-n     DICOM/Supplement_175
-(300A,0650)    UI      PatientSetupUID 1       DICOM/Supplement_175
-(300A,0651)    SQ      WedgeDefinitionSequence 1       DICOM/Supplement_175
-(300A,0652)    FD      RadiationBeamWedgeAngle 1       DICOM/Supplement_175
-(300A,0653)    FD      RadiationBeamWedgeThinEdgeDistance      1       DICOM/Supplement_175
-(300A,0654)    FD      RadiationBeamEffectiveWedgeAngle        1       DICOM/Supplement_175
-(300A,0655)    US      NumberOfWedgePositions  1       DICOM/Supplement_175
-(300A,0656)    SQ      RTBeamLimitingDeviceOpeningSequence     1       DICOM/Supplement_175
-(300A,0657)    US      NumberOfRTBeamLimitingDeviceOpenings    1       DICOM/Supplement_175
-(300A,0658)    SQ      RadiationDosimeterUnitSequence  1       DICOM/Supplement_175
-(300A,0659)    SQ      RTDeviceDistanceReferenceLocationCodeSequence   1       DICOM/Supplement_175
-(300A,065A)    SQ      RadiationDeviceConfigurationAndCommissioningKeySequence 1       DICOM/Supplement_175
-(300A,065B)    SQ      PatientSupportPositionParameterSequence 1       DICOM/Supplement_175
-(300A,065C)    CS      PatientSupportPositionSpecificationMethod       1       DICOM/Supplement_175
-(300A,065D)    SQ      PatientSupportPositionDeviceParameterSequence   1       DICOM/Supplement_175
-(300A,065E)    US      DeviceOrderIndex        1       DICOM/Supplement_175
-(300A,065F)    US      PatientSupportPositionParameterOrderIndex       1       DICOM/Supplement_175
-(300A,0660)    SQ      PatientSupportPositionDeviceToleranceSequence   1       DICOM/Supplement_175
-(300A,0661)    US      PatientSupportPositionToleranceOrderIndex       1       DICOM/Supplement_175
-(300A,0662)    SQ      CompensatorDefinitionSequence   1       DICOM/Supplement_175
-(300A,0663)    CS      CompensatorMapOrientation       1       DICOM/Supplement_175
-(300A,0664)    OF      CompensatorProximalThicknessMap 1       DICOM/Supplement_175
-(300A,0665)    OF      CompensatorDistalThicknessMap   1       DICOM/Supplement_175
-(300A,0666)    FD      CompensatorBasePlaneOffset      1       DICOM/Supplement_175
-(300A,0667)    SQ      CompensatorShapeFabricationCodeSequence 1       DICOM/Supplement_175
-(300A,0668)    SQ      CompensatorShapeSequence        1       DICOM/Supplement_175
-(300A,0669)    FD      RadiationBeamCompensatorMillingToolDiameter     1       DICOM/Supplement_175
-(300A,066A)    SQ      BlockDefinitionSequence 1       DICOM/Supplement_175
-(300A,066B)    OF      BlockEdgeData   1       DICOM/Supplement_175
-(300A,066C)    CS      BlockOrientation        1       DICOM/Supplement_175
-(300A,066D)    FD      RadiationBeamBlockThickness     1       DICOM/Supplement_175
-(300A,066E)    FD      RadiationBeamBlockSlabThickness 1       DICOM/Supplement_175
-(300A,066F)    SQ      BlockEdgeDataSequence   1       DICOM/Supplement_175
-(300A,0670)    US      NumberOfRTAccessoryHolders      1       DICOM/Supplement_175
-(300A,0671)    SQ      GeneralAccessoryDefinitionSequence      1       DICOM/Supplement_175
-(300A,0672)    US      NumberOfGeneralAccessories      1       DICOM/Supplement_175
-(300A,0673)    SQ      BolusDefinitionSequence 1       DICOM/Supplement_175
-(300A,0674)    US      NumberOfBoluses 1       DICOM/Supplement_175
-(300A,0675)    UI      EquipmentFrameOfReferenceUID    1       DICOM/Supplement_175
-(300A,0676)    ST      EquipmentFrameOfReferenceDescription    1       DICOM/Supplement_175
-(300A,0677)    SQ      EquipmentReferencePointCoordinatesSequence      1       DICOM/Supplement_175
-(300A,0678)    SQ      EquipmentReferencePointCodeSequence     1       DICOM/Supplement_175
-(300A,0679)    FD      RTBeamLimitingDeviceAngle       1       DICOM/Supplement_175
-(300A,067A)    FD      SourceRollAngle 1       DICOM/Supplement_175
-(300A,067B)    SQ      RadiationGenerationModeSequence 1       DICOM/Supplement_175
-(300A,067C)    SH      RadiationGenerationModeLabel    1       DICOM/Supplement_175
-(300A,067D)    ST      RadiationGenerationModeDescription      1       DICOM/Supplement_175
-(300A,067E)    SQ      RadiationGenerationModeMachineCodeSequence      1       DICOM/Supplement_175
-(300A,067F)    SQ      RadiationTypeCodeSequence       1       DICOM/Supplement_175
-(300A,0680)    DS      NominalEnergy   1       DICOM/Supplement_175
-(300A,0681)    DS      MinimumNominalEnergy    1       DICOM/Supplement_175
-(300A,0682)    DS      MaximumNominalEnergy    1       DICOM/Supplement_175
-(300A,0683)    SQ      RadiationFluenceModifierCodeSequence    1       DICOM/Supplement_175
-(300A,0684)    SQ      EnergyUnitCodeSequence  1       DICOM/Supplement_175
-(300A,0685)    US      NumberOfRadiationGenerationModes        1       DICOM/Supplement_175
-(300A,0686)    SQ      PatientSupportDevicesSequence   1       DICOM/Supplement_175
-(300A,0687)    US      NumberOfPatientSupportDevices   1       DICOM/Supplement_175
-(300A,0688)    FD      RTBeamModifierDefinitionDistance        1       DICOM/Supplement_175
-(300A,0689)    SQ      BeamAreaLimitSequence   1       DICOM/Supplement_175
-#
-#---------------------------------------------------------------------------
-#
 # Private Creator Data Elements
 #
 (0009-o-FFFF,0000)     UL      PrivateGroupLength      1       PRIVATE
index b754dc78253c44b3db151d84c42bafd740fe0138..bd6135048294a24e81c9ee47a5cf43cbe4e08996 100644 (file)
@@ -1,5 +1,5 @@
 #
-#  Copyright (C) 1994-2013, OFFIS e.V.
+#  Copyright (C) 1994-2020, OFFIS e.V.
 #  All rights reserved.  See COPYRIGHT file for details.
 #
 #  This software and supporting documentation were developed by
@@ -26,6 +26,7 @@
 #   - Circle Cardiovascular Imaging cmr42 3.0 conformance statement
 #   - David Clunie's dicom3tools package, 2002-04-20 snapshot
 #   - Fuji CR console, 3rd release
+#   - GE Vivid S70 version 201 conformance statement
 #   - Intelerad Medical Systems Inc., Image Server
 #   - OCULUS Pentacam 1.17 conformance statement
 #   - Philips Digital Diagnost 1.3 conformance statement
 (0023,"GEMS_STDY_01",74)       SL      NumberOfUpdatesToHeader 1       PrivateTag
 (0023,"GEMS_STDY_01",7d)       SS      IndicatesIfStudyHasCompleteInfo 1       PrivateTag
 
+(7fe1,"GEMS_Ultrasound_MovieGroup_001",1060)   px      IllegalPrivatePixelSequence     1       PrivateTag
+
 (0033,"GEMS_YMHD_01",05)       UN      Unknown 1       PrivateTag
 (0033,"GEMS_YMHD_01",06)       UN      Unknown 1       PrivateTag
 
index 3cc31a4535543c2e58e716565bbd1065ba19e81d..0a970ea8662a89d068e488bb262bc5500ce80072 100644 (file)
@@ -169,6 +169,30 @@ data set trailing padding (not with --write-dataset):
          and items on multiple of i bytes
 \endverbatim
 
+\section cda2dcm_notes NOTES
+
+\subsection cda2dcm_attribute_sources Attribute Sources
+
+The application may be fed with some additional input for filling mandatory (and
+optional) attributes in the new DICOM file like patient, study and series
+information:
+
+\li The \e --key option can be used to add further attributes to the DICOM
+    output file.
+
+\li It is also possible to specify sequences, items and nested
+    attributes using the \e --key option. In these cases, a special "path"
+    notation has to be used. Details on this path notation can be found in the
+    documentation of \b dcmodify.
+
+\li The \e --key option can be present more than once.
+
+\li The value part (after the '=') may be absent causing the attribute to be
+    set with zero length.
+
+\li Please be advised that the \e --key option is applied at the very end, just
+    before saving the DICOM file, so there is no value checking whatsoever.
+
 \section cda2dcm_logging LOGGING
 
 The level of logging output of the various command line tools and underlying
@@ -253,6 +277,6 @@ It is an error if no data dictionary can be loaded.
 
 \section cda2dcm_copyright COPYRIGHT
 
-Copyright (C) 2018 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 2018-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index f432b05e578ff556efb08d3689e23a1693274179..c202d2a8300cfef0544a5233c634d923ad6c8f8e 100644 (file)
@@ -19,7 +19,7 @@ raw data set) to JSON (JavaScript Object Notation).  The output refers to the
 "DICOM JSON Model", which is found in DICOM Part 18 Section F.
 
 If \b dcm2json reads a raw data set (DICOM data without a file format
-meta-header) it will attempt to guess the transfer syntax by examining the
+meta-header), it will attempt to guess the transfer syntax by examining the
 first few bytes of the file.  It is not always possible to correctly guess the
 transfer syntax and it is better to convert a data set to a file format
 whenever possible (using the \b dcmconv utility).  It is also possible to use
@@ -38,79 +38,89 @@ jsonfile-out  JSON output filename (default: stdout)
 
 \subsection dcm2json_general_options general options
 \verbatim
-  -h    --help
-          print this help text and exit
+  -h   --help
+         print this help text and exit
 
-        --version
-          print version information and exit
+       --version
+         print version information and exit
 
-        --arguments
-          print expanded command line arguments
+       --arguments
+         print expanded command line arguments
 
-  -q    --quiet
-          quiet mode, print no warnings and errors
+  -q   --quiet
+         quiet mode, print no warnings and errors
 
-  -v    --verbose
-          verbose mode, print processing details
+  -v   --verbose
+         verbose mode, print processing details
 
-  -d    --debug
-          debug mode, print debug information
+  -d   --debug
+         debug mode, print debug information
 
-  -ll   --log-level  [l]evel: string constant
-          (fatal, error, warn, info, debug, trace)
-          use level l for the logger
+  -ll  --log-level  [l]evel: string constant
+         (fatal, error, warn, info, debug, trace)
+         use level l for the logger
 
-  -lc   --log-config  [f]ilename: string
-          use config file f for the logger
+  -lc  --log-config  [f]ilename: string
+         use config file f for the logger
 \endverbatim
 
 \subsection dcm2json_input_options input options
 \verbatim
 input file format:
 
-  +f    --read-file
-          read file format or data set (default)
+  +f   --read-file
+         read file format or data set (default)
 
-  +fo   --read-file-only
-          read file format only
+  +fo  --read-file-only
+         read file format only
 
-  -f    --read-dataset
-          read data set without file meta information
+  -f   --read-dataset
+         read data set without file meta information
 
 input transfer syntax:
 
-  -t=   --read-xfer-auto
-          use TS recognition (default)
+  -t=  --read-xfer-auto
+         use TS recognition (default)
 
-  -td   --read-xfer-detect
-          ignore TS specified in the file meta header
+  -td  --read-xfer-detect
+         ignore TS specified in the file meta header
 
-  -te   --read-xfer-little
-          read with explicit VR little endian TS
+  -te  --read-xfer-little
+         read with explicit VR little endian TS
 
-  -tb   --read-xfer-big
-          read with explicit VR big endian TS
+  -tb  --read-xfer-big
+         read with explicit VR big endian TS
 
-  -ti   --read-xfer-implicit
-          read with implicit VR little endian TS
+  -ti  --read-xfer-implicit
+         read with implicit VR little endian TS
+\endverbatim
+
+\subsection dcm2json_processing_options processing options
+\verbatim
+encoding of infinity and not-a-number:
+  -es  --encode-strict
+         report error for 'inf' and 'nan' (default)
+
+  -ee  --encode-extended
+         permit 'inf' and 'nan' in JSON numbers
 \endverbatim
 
 \subsection dcm2json_output_options output options
 \verbatim
 output format:
 
-  +fc   --formatted-code
-          enable whitespace formatting (default)
+  +fc  --formatted-code
+         enable whitespace formatting (default)
 
-          # prints additional spaces and newlines for increased
-          # readability
+         # prints additional spaces and newlines for increased
+         # readability
 
-  -fc   --compact-code
-          print only required characters
+  -fc  --compact-code
+         print only required characters
 
-  +m    --write-meta
-          write data set with meta information
-          (warning: not conforming to the DICOM standard)
+  +m   --write-meta
+         write data set with meta information
+         (warning: not conforming to the DICOM standard)
 \endverbatim
 
 \section dcm2json_json_format JSON Format
@@ -277,19 +287,20 @@ the following (see DICOM Part 18 Section F for details):
 \subsection dcm2json_bulk_data Bulk Data
 
 Binary data, i.e. DICOM element values with Value Representations (VR) of OB
-or OW, as well as OD, OF and UN values are by default not written to the JSON
-output because of their size.  Instead, for each element, a new Universally
-Unique Identifier (UUID) is being generated and written as an value of a
-BulkDataURI JSON element.  So far, there is no possibility to write an
-additional file to hold the binary data for each of the binary data chunks.
+or OW, as well as OD, OF, OL, OV and UN values are always written as
+"InlineBinary" (base64 encoding) to the JSON output.  A future version of this
+tool might optionally use a "BulkDataURI" instead, i.e. the WADO-RS URL of a
+bulk data item that contains the element value.  This would be particularly
+useful for large amounts of data, such as pixel data.
 
 \section dcm2json_notes NOTES
 
 \subsection dcm2json_character_encoding Character Encoding
 
-\b dcm2json always tries to output in UTF-8 encoding.  If this is not possible,
-e.g. because there is no support for character set conversion, ASCII is used
-instead (which is a subset of UTF-8).
+As required by the DICOM JSON encoding, \b dcm2json always creates output in
+Unicode UTF-8 encoding and converts DICOM datasets accordingly.  If this is not
+possible, for example because DCMTK has been compiled without either iconv or
+ICU library, an error is returned.
 
 \section dcm2json_logging LOGGING
 
@@ -332,6 +343,34 @@ allows one to summarize common combinations of options/parameters and avoids
 longish and confusing command lines (an example is provided in file
 <em>\<datadir\>/dumppat.txt</em>).
 
+\section dcm2json_exit_codes EXIT CODES
+
+The \b dcm2json utility uses the following exit codes when terminating.  This
+enables the user to check for the reason why the application terminated.
+
+\subsection dcm2json_exit_codes_general general
+\verbatim
+EXITCODE_NO_ERROR                         0
+EXITCODE_COMMANDLINE_SYNTAX_ERROR         1
+\endverbatim
+
+\subsection dcm2json_exit_codes_input_file_errors input file errors
+\verbatim
+EXITCODE_CANNOT_READ_INPUT_FILE          20
+EXITCODE_NO_INPUT_FILES                  21
+\endverbatim
+
+\subsection dcm2json_exit_codes_output_file_errors output file errors
+\verbatim
+EXITCODE_CANNOT_WRITE_OUTPUT_FILE        40
+\endverbatim
+
+\subsection dcm2json_exit_codes_processing_errors processing errors
+\verbatim
+EXITCODE_CANNOT_CONVERT_TO_UNICODE       80
+EXITCODE_CANNOT_WRITE_VALID_JSON         81
+\endverbatim
+
 \section dcm2json_environment ENVIRONMENT
 
 The \b dcm2json utility will attempt to load DICOM data dictionaries specified
@@ -350,6 +389,6 @@ It is an error if no data dictionary can be loaded.
 
 \section dcm2json_copyright COPYRIGHT
 
-Copyright (C) 2016-2017 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 2016-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index f2e58ec86f6bfa45feb28749b9f035a608de71a6..6ed33efb66f719b331d418f08a27ceb9ba3849ff 100644 (file)
@@ -213,7 +213,7 @@ looks like the following:
       <item card="3">
         <element tag="0028,3002" vr="xs" vm="3" len="6"
                  name="LUTDescriptor">
-          256\\0\\8
+          256\0\8
         </element>
         ...
       </item>
@@ -261,7 +261,7 @@ standard, part 19 ("Application Hosting").
 \subsection dcm2xml_bulk_data Bulk Data
 
 Binary data, i.e. DICOM element values with Value Representations (VR) of OB
-or OW, as well as OD, OF, OV and UN values are by default not written to the
+or OW, as well as OD, OF, OL, OV and UN values are by default not written to the
 XML output because of their size.  Instead, for each element, a new Universally
 Unique Identifier (UUID) is being generated and written as an attribute of a
 \<BulkData\> XML element.  So far, there is no possibility to write an
@@ -273,17 +273,17 @@ available in future versions of \b dcm2xml.
 In addition, Supplement 163 (Store Over the Web by Representational State
 Transfer Services) introduces a new \<InlineBinary\> XML element that allows
 for encoding binary data as Base64.  Currently, the command line option
-\e --encode-base64 enables this encoding for the following VRs: OB, OD, OF, OV,
-OW and UN.
+\e --encode-base64 enables this encoding for the following VRs: OB, OD, OF, OL,
+OV, OW and UN.
 
 \subsection dcm2xml_known_issues Known Issues
 
 In addition to what is written in the above section on "Bulk Data", there are
 further known issues with the current implementation of the Native DICOM Model
-format.  For example, large element values with a VR other than OB, OD, OF, OV,
-OW or UN are currently never written as bulk data, although it might be useful,
-e.g. for very long text elements (especially UT) or very long numeric fields
-(of various VRs).
+format.  For example, large element values with a VR other than OB, OD, OF, OL,
+OV, OW or UN are currently never written as bulk data, although it might be
+useful, e.g. for very long text elements (especially UT) or very long numeric
+fields (of various VRs).
 
 \section dcm2xml_notes NOTES
 
@@ -391,6 +391,6 @@ It is an error if no data dictionary can be loaded.
 
 \section dcm2xml_copyright COPYRIGHT
 
-Copyright (C) 2002-2019 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 2002-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index 3c947313f19698889711d953ca34e56c32f1b5a7..bb266eabadaf9a92709d0a7b3783512219b0bde1 100644 (file)
@@ -242,11 +242,11 @@ other processing options:
 \verbatim
 output file format:
 
-  +F   --write-file
-         write file format (default)
-
   +Fm  --write-new-meta-info
-         write file format with new meta information
+         write file format with new meta information (default)
+
+  +F   --write-file
+         write file format
 
   -F   --write-dataset
          write data set without file meta information
@@ -387,6 +387,6 @@ It is an error if no data dictionary can be loaded.
 
 \section dcmconv_copyright COPYRIGHT
 
-Copyright (C) 1994-2017 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 1994-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index f876431484e2adcbd9daf9b9acf2f8415c63efe7..69d740012f8000a8cd8e9d2f7bb756308462a30a 100644 (file)
@@ -60,6 +60,9 @@ However, if specifying an item number like '5', all 6 items (counted from zero)
 can be (and are) automatically generated in insert mode.  If already 2 items
 would exist, the rest (4) would be inserted.
 
+\b dcmodify does not work on directories, i.e. the parameter \e dcmfile-in...
+must not include directory names.
+
 Please note that there are some issues concerning the modification of private
 tags (see PRIVATE TAGS section) and for changing UIDs (CHANGING UIDs section).
 
@@ -362,6 +365,12 @@ When choosing the \e -gin option, the related metaheader tag ('Media Storage
 SOP Instance UID') is updated automatically.  This behavior cannot be
 disabled.
 
+When working on multiple input files, \b dcmodify processes each file
+in isolated fashion, i.e. it will generate UIDs for each single file.  For
+example, when using the \e -gst option, \b dcmodify will insert a different
+Study Instance UID into each file instead of generating a single one and
+writing it to each file that is being processed.
+
 \section dcmodify_creating_new_files CREATING NEW FILES
 
 Option \e --create-file lets \b dcmodify create a file if it does not already
index b1ad195eff52d845028b48f64e5321431db5e3ff..0029114fb80b39a5e831c86ac7924b65433af83a 100644 (file)
@@ -199,13 +199,13 @@ VR:    Value Representation must be written as 2 characters as in
        between the two characters.  If the VR can be determined from
        the tag, this part of a line is optional.
 Value: There are several rules for writing values:
-       1. US, SS, SL, UL, FD, FL, OD, OF and OL are written as decimal
-          strings that can be read by scanf().
+       1. US, SS, UL, SL, UV, SV, FD, FL, OD, OF, OL and OV are written
+          as decimal strings that can be read by scanf().
        2. AT is written as '(gggg,eeee)' with additional spaces
           stripped off automatically and gggg and eeee being decimal
           strings that can be read by scanf().
        3. OB and OW values are written as byte or word hexadecimal
-          values separated by '\\' character.  Alternatively, OB or OW
+          values separated by '\' character.  Alternatively, OB or OW
           values can be read from a separate file by writing the
           filename prefixed by a '=' character (e.g. '=largepix.dat').
           The contents of the file will be read as is.  By default, OW
@@ -225,22 +225,24 @@ Value: There are several rules for writing values:
           line.  Anything after the ']' is interpreted as comment.
        7. '(' and '<' are interpreted special and may not be used when
           writing an input file by hand as beginning characters of a
-          string.  Multiple Value are separated by '\\'.  The lines
+          string.  Multiple Value are separated by '\'.  The lines
           need not be sorted into ascending tag order.  References in
           DICOM Directories are not supported.  Semantic errors are
           not detected.
 \endverbatim
 
-\subsection dump2dcm_notes_example Example
+\subsection dump2dcm_notes_examples Examples
+
+The following lines show valid examples of the syntax described above:
 
 \verbatim
  (0008,0020) DA [19921012]            #  8, 1 StudyDate
  (0008,0016) UI =MRImageStorage       # 26, 1 SOPClassUID
  (0002,0012) UI [1.2.276.0.7230010.100.1.1]
- (0020,0032) DS [0.0\\0.0]             #  8, 2 ImagePositionPatient
+ (0020,0032) DS [0.0\0.0]             #  8, 2 ImagePositionPatient
  (0028,0009) AT (3004,000c)           #  4, 1 FrameIncrementPointer
  (0028,0010) US 256                   #  4, 1 Rows
- (0002,0001) OB 01\\00
+ (0002,0001) OB 01\00
 \endverbatim
 
 \subsection dump2dcm_limitations Limitations
@@ -312,6 +314,6 @@ It is an error if no data dictionary can be loaded.
 
 \section dump2dcm_copyright COPYRIGHT
 
-Copyright (C) 1996-2016 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 1996-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index 4c84e104fe7dbdc985313f5a5dff743613f8dd68..125b8749b63ac49449c692190fa4d90ef184d780 100644 (file)
@@ -246,11 +246,14 @@ order:
     enabled, no automatic attribute insertion will take place.
 
 \li The \e --key option can be used to add further attributes to the DICOM
-    output file. This option is applied at the very end, just before saving the
-    DICOM file. It is also possible to specify sequences, items and nested
+    output file. It is also possible to specify sequences, items and nested
     attributes using the \e --key option. In these cases, a special "path"
     notation has to be used. Details on this path notation can be found in the
-    documentation of \b dcmodify.
+    documentation of \b dcmodify. The \e --key option can be present more than
+    once. The value part (after the '=') may be absent causing the attribute to
+    be set with zero length. Please be advised that the \e --key option is
+    applied at the very end, just before saving the DICOM file, so there is no
+    value checking whatsoever.
 
 \subsection img2dcm_uids UIDs
 
@@ -496,6 +499,6 @@ images
 
 \section img2dcm_copyright COPYRIGHT
 
-Copyright (C) 2007-2019 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 2007-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index 282476d72bcb8e2a8d1809f51f559c9e3d43db7e..5451d207d20866b990c600aa3f1aa7d8e9a8c21e 100644 (file)
@@ -159,6 +159,30 @@ data set trailing padding (not with --write-dataset):
          and items on multiple of i bytes
 \endverbatim
 
+\section pdf2dcm_notes NOTES
+
+\subsection pdf2dcm_attribute_sources Attribute Sources
+
+The application may be fed with some additional input for filling mandatory (and
+optional) attributes in the new DICOM file like patient, study and series
+information:
+
+\li The \e --key option can be used to add further attributes to the DICOM
+    output file.
+
+\li It is also possible to specify sequences, items and nested
+    attributes using the \e --key option. In these cases, a special "path"
+    notation has to be used. Details on this path notation can be found in the
+    documentation of \b dcmodify.
+
+\li The \e --key option can be present more than once.
+
+\li The value part (after the '=') may be absent causing the attribute to be
+    set with zero length.
+
+\li Please be advised that the \e --key option is applied at the very end, just
+    before saving the DICOM file, so there is no value checking whatsoever.
+
 \section pdf2dcm_logging LOGGING
 
 The level of logging output of the various command line tools and underlying
@@ -247,6 +271,6 @@ It is an error if no data dictionary can be loaded.
 
 \section pdf2dcm_copyright COPYRIGHT
 
-Copyright (C) 2005-2018 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 2005-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index e47a7c301ad273bb7ddab3477cbd0b43b23cec03..11571601b74bc0ff491b81daa6812c852c7b0f2b 100644 (file)
@@ -179,6 +179,30 @@ data set trailing padding (not with --write-dataset):
          and items on multiple of i bytes
 \endverbatim
 
+\section stl2dcm_notes NOTES
+
+\subsection stl2dcm_attribute_sources Attribute Sources
+
+The application may be fed with some additional input for filling mandatory (and
+optional) attributes in the new DICOM file like patient, study and series
+information:
+
+\li The \e --key option can be used to add further attributes to the DICOM
+    output file.
+
+\li It is also possible to specify sequences, items and nested
+    attributes using the \e --key option. In these cases, a special "path"
+    notation has to be used. Details on this path notation can be found in the
+    documentation of \b dcmodify.
+
+\li The \e --key option can be present more than once.
+
+\li The value part (after the '=') may be absent causing the attribute to be
+    set with zero length.
+
+\li Please be advised that the \e --key option is applied at the very end, just
+    before saving the DICOM file, so there is no value checking whatsoever.
+
 \section stl2dcm_logging LOGGING
 
 The level of logging output of the various command line tools and underlying
@@ -263,6 +287,6 @@ It is an error if no data dictionary can be loaded.
 
 \section stl2dcm_copyright COPYRIGHT
 
-Copyright (C) 2018 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 2018-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index 02fea6cdbc0609a2045caf791ed76c9f4ddc07c9..b48d870ab563f707d18643335518343e0af8fc51 100644 (file)
@@ -195,7 +195,7 @@ The basic structure of the XML input expected looks like the following:
       <item card="3">
         <element tag="0028,3002" vr="xs" vm="3" len="6"
                  name="LUTDescriptor">
-          256\\0\\8
+          256\0\8
         </element>
         ...
       </item>
@@ -342,6 +342,6 @@ It is an error if no data dictionary can be loaded.
 
 \section xml2dcm_copyright COPYRIGHT
 
-Copyright (C) 2003-2019 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 2003-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index ca28195a25ea3cd7d5ffa3e63e003aaf2365452b..55712b930741d38a43f2c30c2bcadd43707a091c 100644 (file)
@@ -247,6 +247,14 @@ class DCMTK_DCMDATA_EXPORT DcmByteString: public DcmElement
      */
     virtual OFCondition putString(const char *stringVal);
 
+    /** set element value at specific VM position in the given character string.
+     *  @param stringVal input character string (possibly multi-valued)
+     *  @param pos position (0..vm) where the value should be inserted
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition putOFStringAtPos(const OFString& stringVal,
+                                         const unsigned long pos = 0);
+
     /** set element value from the given character string.
      *  The length of the string has to be specified explicitly. The string can, therefore,
      *  also contain more than one NULL byte.
index 60b5de50f612431f458b321f49fbfbabd2068df5..5d99148365d2c8cab31fba0af4f9f212eccdc848 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1997-2018, OFFIS e.V.
+ *  Copyright (C) 1997-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -92,6 +92,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition decode(
@@ -99,7 +103,8 @@ public:
     DcmPixelSequence * pixSeq,
     DcmPolymorphOBOW& uncompressedPixelData,
     const DcmCodecParameter * cp,
-    const DcmStack& objStack) const = 0;
+    const DcmStack & objStack,
+    OFBool& removeOldRep) const = 0;
 
   /** decompresses a single frame from the given pixel sequence and
    *  stores the result in the given buffer.
@@ -149,6 +154,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition encode(
@@ -157,7 +166,8 @@ public:
     const DcmRepresentationParameter * toRepParam,
     DcmPixelSequence * & pixSeq,
     const DcmCodecParameter *cp,
-    DcmStack & objStack) const = 0;
+    DcmStack & objStack,
+    OFBool& removeOldRep) const = 0;
 
   /** transcodes (re-compresses) the given compressed DICOM image and stores
    *  the result in the given toPixSeq element.
@@ -171,6 +181,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition encode(
@@ -180,7 +194,8 @@ public:
     const DcmRepresentationParameter * toRepParam,
     DcmPixelSequence * & toPixSeq,
     const DcmCodecParameter * cp,
-    DcmStack & objStack) const = 0;
+    DcmStack & objStack,
+    OFBool& removeOldRep) const = 0;
 
   /** checks if this codec is able to convert from the
    *  given current transfer syntax to the given new
@@ -345,6 +360,10 @@ public:
    *  @param uncompressedPixelData uncompressed pixel data stored in this element
    *  @param pixelStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   static OFCondition decode(
@@ -352,7 +371,8 @@ public:
     const DcmRepresentationParameter * fromParam,
     DcmPixelSequence * fromPixSeq,
     DcmPolymorphOBOW& uncompressedPixelData,
-    DcmStack & pixelStack);
+    DcmStack & pixelStack,
+    OFBool& removeOldRep);
 
   /** looks for a codec that is able to decode from the given transfer syntax
    *  and calls the decodeFrame() method of the codec.  A read lock on the list of
@@ -405,6 +425,10 @@ public:
    *    allocated on heap) returned in this parameter upon success.
    *  @param pixelStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   static OFCondition encode(
@@ -414,7 +438,8 @@ public:
     const E_TransferSyntax toRepType,
     const DcmRepresentationParameter * toRepParam,
     DcmPixelSequence * & pixSeq,
-    DcmStack & pixelStack);
+    DcmStack & pixelStack,
+    OFBool& removeOldRep);
 
   /** looks for a codec that is able to transcode (re-compresses)
    *  from the given transfer syntax to the given transfer syntax
@@ -431,6 +456,10 @@ public:
    *    allocated on heap) returned in this parameter upon success.
    *  @param pixelStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   static OFCondition encode(
@@ -440,7 +469,8 @@ public:
     const E_TransferSyntax toRepType,
     const DcmRepresentationParameter * toRepParam,
     DcmPixelSequence * & toPixSeq,
-    DcmStack & pixelStack);
+    DcmStack & pixelStack,
+    OFBool& removeOldRep);
 
   /** looks for a codec that claims to be able to convert
    *  between the given transfer syntaxes.
index 63ea8be9374af487e712f6da0b4aa53e1c61b893..f46ff71fca2375fe32dec495c28215563b857237 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2018, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -281,20 +281,6 @@ class DCMTK_DCMDATA_EXPORT DcmDataset
     virtual OFCondition writeJson(STD_NAMESPACE ostream &out,
                                   DcmJsonFormat &format);
 
-    /** write object in JSON format.
-     *  @tparam Format the formatter class, e.g. DcmJsonFormatPretty.
-     *    Will be deduced automatically.
-     *  @param out output stream to which the JSON document is written
-     *  @param format used to format and customize the output
-     *  @return status, EC_Normal if successful, an error code otherwise
-     */
-    template<typename Format>
-    OFCondition writeJson(STD_NAMESPACE ostream &out,
-                          Format format)
-    {
-        return writeJson(out, OFstatic_cast(DcmJsonFormat&, format));
-    }
-
     /** load object from a DICOM file.
      *  This method only supports DICOM objects stored as a dataset, i.e. without meta header.
      *  Use DcmFileFormat::loadFile() to load files with meta header.
index 11751552ef458c37f880c15a1677bd25e52ded76..a65b51ce638db05561c5485695be448267b6223e 100644 (file)
@@ -4,7 +4,7 @@
 **
 **   User: joergr
 **   Host: thinkpad
-**   Date: 2019-08-07 18:58:15
+**   Date: 2020-11-24 14:49:52
 **   Prog: /home/joergr/Source/dcmtk-full/public/dcmdata/libsrc/mkdeftag
 **
 **   From: ../data/dicom.dic
 
 #include "dcmtk/dcmdata/dctagkey.h"
 
-#define DCM_DICT_DEFTAG_BUILD_DATE "2019-08-07 18:58:15"
+#define DCM_DICT_DEFTAG_BUILD_DATE "2020-11-24 14:49:52"
 
 
 /*
 ** Fixed Tags in ascending (gggg,eeee) order.
-** Number of entries: 4722
+** Number of entries: 4829
 ** Tags with a repeating component (repeating tags) are listed later.
 */
 #define DCM_CommandGroupLength                   DcmTagKey(0x0000, 0x0000)
 #define DCM_SourceApplicationEntityTitle         DcmTagKey(0x0002, 0x0016)
 #define DCM_SendingApplicationEntityTitle        DcmTagKey(0x0002, 0x0017)
 #define DCM_ReceivingApplicationEntityTitle      DcmTagKey(0x0002, 0x0018)
+#define DCM_SourcePresentationAddress            DcmTagKey(0x0002, 0x0026)
+#define DCM_SendingPresentationAddress           DcmTagKey(0x0002, 0x0027)
+#define DCM_ReceivingPresentationAddress         DcmTagKey(0x0002, 0x0028)
+#define DCM_RTVMetaInformationVersion            DcmTagKey(0x0002, 0x0031)
+#define DCM_RTVCommunicationSOPClassUID          DcmTagKey(0x0002, 0x0032)
+#define DCM_RTVCommunicationSOPInstanceUID       DcmTagKey(0x0002, 0x0033)
+#define DCM_RTVSourceIdentifier                  DcmTagKey(0x0002, 0x0035)
+#define DCM_RTVFlowIdentifier                    DcmTagKey(0x0002, 0x0036)
+#define DCM_RTVFlowRTPSamplingRate               DcmTagKey(0x0002, 0x0037)
+#define DCM_RTVFlowActualFrameDuration           DcmTagKey(0x0002, 0x0038)
 #define DCM_PrivateInformationCreatorUID         DcmTagKey(0x0002, 0x0100)
 #define DCM_PrivateInformation                   DcmTagKey(0x0002, 0x0102)
 #define DCM_FileSetID                            DcmTagKey(0x0004, 0x1130)
 #define DCM_ReferencedTransferSyntaxUIDInFile    DcmTagKey(0x0004, 0x1512)
 #define DCM_ReferencedRelatedGeneralSOPClassUIDInFile DcmTagKey(0x0004, 0x151a)
 #define DCM_RETIRED_NumberOfReferences           DcmTagKey(0x0004, 0x1600)
+#define DCM_CurrentFrameFunctionalGroupsSequence DcmTagKey(0x0006, 0x0001)
 #define DCM_RETIRED_LengthToEnd                  DcmTagKey(0x0008, 0x0001)
 #define DCM_SpecificCharacterSet                 DcmTagKey(0x0008, 0x0005)
 #define DCM_LanguageCodeSequence                 DcmTagKey(0x0008, 0x0006)
 #define DCM_RETIRED_AnatomicStructureSpaceOrRegionModifierCodeSequenceTrial DcmTagKey(0x0008, 0x225a)
 #define DCM_RETIRED_OnAxisBackgroundAnatomicStructureCodeSequenceTrial DcmTagKey(0x0008, 0x225c)
 #define DCM_AlternateRepresentationSequence      DcmTagKey(0x0008, 0x3001)
+#define DCM_AvailableTransferSyntaxUID           DcmTagKey(0x0008, 0x3002)
 #define DCM_IrradiationEventUID                  DcmTagKey(0x0008, 0x3010)
 #define DCM_SourceIrradiationEventSequence       DcmTagKey(0x0008, 0x3011)
 #define DCM_RadiopharmaceuticalAdministrationEventUID DcmTagKey(0x0008, 0x3012)
 #define DCM_GPSAreaInformation                   DcmTagKey(0x0016, 0x008c)
 #define DCM_GPSDateStamp                         DcmTagKey(0x0016, 0x008d)
 #define DCM_GPSDifferential                      DcmTagKey(0x0016, 0x008e)
+#define DCM_LightSourcePolarization              DcmTagKey(0x0016, 0x1001)
+#define DCM_EmitterColorTemperature              DcmTagKey(0x0016, 0x1002)
+#define DCM_ContactMethod                        DcmTagKey(0x0016, 0x1003)
+#define DCM_ImmersionMedia                       DcmTagKey(0x0016, 0x1004)
+#define DCM_OpticalMagnificationFactor           DcmTagKey(0x0016, 0x1005)
 #define DCM_ContrastBolusAgent                   DcmTagKey(0x0018, 0x0010)
 #define DCM_ContrastBolusAgentSequence           DcmTagKey(0x0018, 0x0012)
 #define DCM_ContrastBolusT1Relaxivity            DcmTagKey(0x0018, 0x0013)
 #define DCM_RETIRED_AcquisitionComments          DcmTagKey(0x0018, 0x4000)
 #define DCM_OutputPower                          DcmTagKey(0x0018, 0x5000)
 #define DCM_TransducerData                       DcmTagKey(0x0018, 0x5010)
+#define DCM_TransducerIdentificationSequence     DcmTagKey(0x0018, 0x5011)
 #define DCM_FocusDepth                           DcmTagKey(0x0018, 0x5012)
 #define DCM_ProcessingFunction                   DcmTagKey(0x0018, 0x5020)
 #define DCM_RETIRED_PostprocessingFunction       DcmTagKey(0x0018, 0x5021)
 #define DCM_ReasonForVisitCodeSequence           DcmTagKey(0x0032, 0x1067)
 #define DCM_RequestedContrastAgent               DcmTagKey(0x0032, 0x1070)
 #define DCM_RETIRED_StudyComments                DcmTagKey(0x0032, 0x4000)
+#define DCM_FlowIdentifierSequence               DcmTagKey(0x0034, 0x0001)
+#define DCM_FlowIdentifier                       DcmTagKey(0x0034, 0x0002)
+#define DCM_FlowTransferSyntaxUID                DcmTagKey(0x0034, 0x0003)
+#define DCM_FlowRTPSamplingRate                  DcmTagKey(0x0034, 0x0004)
+#define DCM_SourceIdentifier                     DcmTagKey(0x0034, 0x0005)
+#define DCM_FrameOriginTimestamp                 DcmTagKey(0x0034, 0x0007)
+#define DCM_IncludesImagingSubject               DcmTagKey(0x0034, 0x0008)
+#define DCM_FrameUsefulnessGroupSequence         DcmTagKey(0x0034, 0x0009)
+#define DCM_RealTimeBulkDataFlowSequence         DcmTagKey(0x0034, 0x000a)
+#define DCM_CameraPositionGroupSequence          DcmTagKey(0x0034, 0x000b)
+#define DCM_IncludesInformation                  DcmTagKey(0x0034, 0x000c)
+#define DCM_TimeOfFrameGroupSequence             DcmTagKey(0x0034, 0x000d)
 #define DCM_ReferencedPatientAliasSequence       DcmTagKey(0x0038, 0x0004)
 #define DCM_VisitStatusID                        DcmTagKey(0x0038, 0x0008)
 #define DCM_AdmissionID                          DcmTagKey(0x0038, 0x0010)
 #define DCM_MultiplexedAudioChannelsDescriptionCodeSequence DcmTagKey(0x003a, 0x0300)
 #define DCM_ChannelIdentificationCode            DcmTagKey(0x003a, 0x0301)
 #define DCM_ChannelMode                          DcmTagKey(0x003a, 0x0302)
+#define DCM_MultiplexGroupUID                    DcmTagKey(0x003a, 0x0310)
+#define DCM_PowerlineFrequency                   DcmTagKey(0x003a, 0x0311)
+#define DCM_ChannelImpedanceSequence             DcmTagKey(0x003a, 0x0312)
+#define DCM_ImpedanceValue                       DcmTagKey(0x003a, 0x0313)
+#define DCM_ImpedanceMeasurementDateTime         DcmTagKey(0x003a, 0x0314)
+#define DCM_ImpedanceMeasurementFrequency        DcmTagKey(0x003a, 0x0315)
+#define DCM_ImpedanceMeasurementCurrentType      DcmTagKey(0x003a, 0x0316)
 #define DCM_ScheduledStationAETitle              DcmTagKey(0x0040, 0x0001)
 #define DCM_ScheduledProcedureStepStartDate      DcmTagKey(0x0040, 0x0002)
 #define DCM_ScheduledProcedureStepStartTime      DcmTagKey(0x0040, 0x0003)
 #define DCM_RETIRED_RelationshipSequenceTrial    DcmTagKey(0x0040, 0xa731)
 #define DCM_RETIRED_RelationshipTypeCodeSequenceTrial DcmTagKey(0x0040, 0xa732)
 #define DCM_RETIRED_LanguageCodeSequenceTrial    DcmTagKey(0x0040, 0xa744)
+#define DCM_TabulatedValuesSequence              DcmTagKey(0x0040, 0xa801)
+#define DCM_NumberOfTableRows                    DcmTagKey(0x0040, 0xa802)
+#define DCM_NumbeOfTableColumns                  DcmTagKey(0x0040, 0xa803)
+#define DCM_TableRowNumber                       DcmTagKey(0x0040, 0xa804)
+#define DCM_TableColumnNumber                    DcmTagKey(0x0040, 0xa805)
+#define DCM_TableRowDefinitionSequence           DcmTagKey(0x0040, 0xa806)
+#define DCM_TableColumnDefinitionSequence        DcmTagKey(0x0040, 0xa807)
+#define DCM_CellValuesSequence                   DcmTagKey(0x0040, 0xa808)
 #define DCM_RETIRED_UniformResourceLocatorTrial  DcmTagKey(0x0040, 0xa992)
 #define DCM_WaveformAnnotationSequence           DcmTagKey(0x0040, 0xb020)
 #define DCM_TemplateIdentifier                   DcmTagKey(0x0040, 0xdb00)
 #define DCM_ModelModification                    DcmTagKey(0x0068, 0x7001)
 #define DCM_ModelMirroring                       DcmTagKey(0x0068, 0x7002)
 #define DCM_ModelUsageCodeSequence               DcmTagKey(0x0068, 0x7003)
+#define DCM_ModelGroupUID                        DcmTagKey(0x0068, 0x7004)
+#define DCM_RelativeURIReferenceWithinEncapsulatedDocument DcmTagKey(0x0068, 0x7005)
 #define DCM_GraphicAnnotationSequence            DcmTagKey(0x0070, 0x0001)
 #define DCM_GraphicLayer                         DcmTagKey(0x0070, 0x0002)
 #define DCM_BoundingBoxAnnotationUnits           DcmTagKey(0x0070, 0x0003)
 #define DCM_SelectorSSValue                      DcmTagKey(0x0072, 0x007e)
 #define DCM_SelectorUIValue                      DcmTagKey(0x0072, 0x007f)
 #define DCM_SelectorCodeSequenceValue            DcmTagKey(0x0072, 0x0080)
+#define DCM_SelectorOVValue                      DcmTagKey(0x0072, 0x0081)
+#define DCM_SelectorSVValue                      DcmTagKey(0x0072, 0x0082)
+#define DCM_SelectorUVValue                      DcmTagKey(0x0072, 0x0083)
 #define DCM_NumberOfScreens                      DcmTagKey(0x0072, 0x0100)
 #define DCM_NominalScreenDefinitionSequence      DcmTagKey(0x0072, 0x0102)
 #define DCM_NumberOfVerticalPixels               DcmTagKey(0x0072, 0x0104)
 #define DCM_RepeatFractionCycleLength            DcmTagKey(0x300a, 0x007a)
 #define DCM_FractionPattern                      DcmTagKey(0x300a, 0x007b)
 #define DCM_NumberOfBeams                        DcmTagKey(0x300a, 0x0080)
-#define DCM_BeamDoseSpecificationPoint           DcmTagKey(0x300a, 0x0082)
+#define DCM_RETIRED_BeamDoseSpecificationPoint   DcmTagKey(0x300a, 0x0082)
 #define DCM_ReferencedDoseReferenceUID           DcmTagKey(0x300a, 0x0083)
 #define DCM_BeamDose                             DcmTagKey(0x300a, 0x0084)
 #define DCM_BeamMeterset                         DcmTagKey(0x300a, 0x0086)
 #define DCM_ScanSpotReorderingAllowed            DcmTagKey(0x300a, 0x0395)
 #define DCM_ScanSpotMetersetWeights              DcmTagKey(0x300a, 0x0396)
 #define DCM_ScanningSpotSize                     DcmTagKey(0x300a, 0x0398)
+#define DCM_ScanSpotSizesDelivered               DcmTagKey(0x300a, 0x0399)
 #define DCM_NumberOfPaintings                    DcmTagKey(0x300a, 0x039a)
 #define DCM_IonToleranceTableSequence            DcmTagKey(0x300a, 0x03a0)
 #define DCM_IonBeamSequence                      DcmTagKey(0x300a, 0x03a2)
 #define DCM_GeneralAccessoryType                 DcmTagKey(0x300a, 0x0423)
 #define DCM_GeneralAccessoryNumber               DcmTagKey(0x300a, 0x0424)
 #define DCM_SourceToGeneralAccessoryDistance     DcmTagKey(0x300a, 0x0425)
+#define DCM_IsocenterToGeneralAccessoryDistance  DcmTagKey(0x300a, 0x0426)
 #define DCM_ApplicatorGeometrySequence           DcmTagKey(0x300a, 0x0431)
 #define DCM_ApplicatorApertureShape              DcmTagKey(0x300a, 0x0432)
 #define DCM_ApplicatorOpening                    DcmTagKey(0x300a, 0x0433)
 #define DCM_RTBeamLimitingDeviceProximalDistance DcmTagKey(0x300a, 0x0642)
 #define DCM_RTBeamLimitingDeviceDistalDistance   DcmTagKey(0x300a, 0x0643)
 #define DCM_ParallelRTBeamDelimiterDeviceOrientationLabelCodeSequence DcmTagKey(0x300a, 0x0644)
-#define DCM_BeamsModifierOrientationAngle        DcmTagKey(0x300a, 0x0645)
+#define DCM_BeamModifierOrientationAngle         DcmTagKey(0x300a, 0x0645)
 #define DCM_FixedRTBeamDelimiterDeviceSequence   DcmTagKey(0x300a, 0x0646)
 #define DCM_ParallelRTBeamDelimiterDeviceSequence DcmTagKey(0x300a, 0x0647)
 #define DCM_NumberOfParallelRTBeamDelimiters     DcmTagKey(0x300a, 0x0648)
 #define DCM_NumberOfPatientSupportDevices        DcmTagKey(0x300a, 0x0687)
 #define DCM_RTBeamModifierDefinitionDistance     DcmTagKey(0x300a, 0x0688)
 #define DCM_BeamAreaLimitSequence                DcmTagKey(0x300a, 0x0689)
+#define DCM_ReferencedRTPrescriptionSequence     DcmTagKey(0x300a, 0x068a)
+#define DCM_TreatmentSessionUID                  DcmTagKey(0x300a, 0x0700)
+#define DCM_RTRadiationUsage                     DcmTagKey(0x300a, 0x0701)
+#define DCM_ReferencedRTRadiationSetSequence     DcmTagKey(0x300a, 0x0702)
+#define DCM_ReferencedRTRadiationRecordSequence  DcmTagKey(0x300a, 0x0703)
+#define DCM_RTRadiationSetDeliveryNumber         DcmTagKey(0x300a, 0x0704)
+#define DCM_ClinicalFractionNumber               DcmTagKey(0x300a, 0x0705)
+#define DCM_RTTreatmentFractionCompletionStatus  DcmTagKey(0x300a, 0x0706)
+#define DCM_RTRadiationSetUsage                  DcmTagKey(0x300a, 0x0707)
+#define DCM_TreatmentDeliveryContinuationFlag    DcmTagKey(0x300a, 0x0708)
+#define DCM_TreatmentRecordContentOrigin         DcmTagKey(0x300a, 0x0709)
+#define DCM_RTTreatmentTerminationStatus         DcmTagKey(0x300a, 0x0714)
+#define DCM_RTTreatmentTerminationReasonCodeSequence DcmTagKey(0x300a, 0x0715)
+#define DCM_MachineSpecificTreatmentTerminationCodeSequence DcmTagKey(0x300a, 0x0716)
+#define DCM_RTRadiationSalvageRecordControlPointSequence DcmTagKey(0x300a, 0x0722)
+#define DCM_StartingMetersetValueKnownFlag       DcmTagKey(0x300a, 0x0723)
+#define DCM_TreatmentTerminationDescription      DcmTagKey(0x300a, 0x0730)
+#define DCM_TreatmentToleranceViolationSequence  DcmTagKey(0x300a, 0x0731)
+#define DCM_TreatmentToleranceViolationCategory  DcmTagKey(0x300a, 0x0732)
+#define DCM_TreatmentToleranceViolationAttributeSequence DcmTagKey(0x300a, 0x0733)
+#define DCM_TreatmentToleranceViolationDescription DcmTagKey(0x300a, 0x0734)
+#define DCM_TreatmentToleranceViolationIdentification DcmTagKey(0x300a, 0x0735)
+#define DCM_TreatmentToleranceViolationDateTime  DcmTagKey(0x300a, 0x0736)
+#define DCM_RecordedRTControlPointDateTime       DcmTagKey(0x300a, 0x073a)
+#define DCM_ReferencedRadiationRTControlPointIndex DcmTagKey(0x300a, 0x073b)
+#define DCM_AlternateValueSequence               DcmTagKey(0x300a, 0x073e)
+#define DCM_ConfirmationSequence                 DcmTagKey(0x300a, 0x073f)
+#define DCM_InterlockSequence                    DcmTagKey(0x300a, 0x0740)
+#define DCM_InterlockDateTime                    DcmTagKey(0x300a, 0x0741)
+#define DCM_InterlockDescription                 DcmTagKey(0x300a, 0x0742)
+#define DCM_InterlockOriginatingDeviceSequence   DcmTagKey(0x300a, 0x0743)
+#define DCM_InterlockCodeSequence                DcmTagKey(0x300a, 0x0744)
+#define DCM_InterlockResolutionCodeSequence      DcmTagKey(0x300a, 0x0745)
+#define DCM_InterlockResolutionUserSequence      DcmTagKey(0x300a, 0x0746)
+#define DCM_OverrideDateTime                     DcmTagKey(0x300a, 0x0760)
+#define DCM_TreatmentToleranceViolationTypeCodeSequence DcmTagKey(0x300a, 0x0761)
+#define DCM_TreatmentToleranceViolationCauseCodeSequence DcmTagKey(0x300a, 0x0762)
+#define DCM_MeasuredMetersetToDoseMappingSequence DcmTagKey(0x300a, 0x0772)
+#define DCM_ReferencedExpectedInVivoMeasurementValueIndex DcmTagKey(0x300a, 0x0773)
+#define DCM_DoseMeasurementDeviceCodeSequence    DcmTagKey(0x300a, 0x0774)
+#define DCM_AdditionalParameterRecordingInstanceSequence DcmTagKey(0x300a, 0x0780)
+#define DCM_InterlockOriginDescription           DcmTagKey(0x300a, 0x0783)
 #define DCM_ReferencedRTPlanSequence             DcmTagKey(0x300c, 0x0002)
 #define DCM_ReferencedBeamSequence               DcmTagKey(0x300c, 0x0004)
 #define DCM_ReferencedBeamNumber                 DcmTagKey(0x300c, 0x0006)
 #define DCM_SegmentAnnotationTypeCodeSequence    DcmTagKey(0x3010, 0x002c)
 #define DCM_DeviceLabel                          DcmTagKey(0x3010, 0x002d)
 #define DCM_DeviceTypeCodeSequence               DcmTagKey(0x3010, 0x002e)
+#define DCM_SegmentAnnotationTypeModifierCodeSequence DcmTagKey(0x3010, 0x002f)
 #define DCM_PatientEquipmentRelationshipCodeSequence DcmTagKey(0x3010, 0x0030)
 #define DCM_ReferencedFiducialsUID               DcmTagKey(0x3010, 0x0031)
 #define DCM_PatientTreatmentOrientationSequence  DcmTagKey(0x3010, 0x0032)
 #define DCM_IntendedStartDayOfWeek               DcmTagKey(0x3010, 0x0086)
 #define DCM_WeekdayFractionPatternSequence       DcmTagKey(0x3010, 0x0087)
 #define DCM_DeliveryTimeStructureCodeSequence    DcmTagKey(0x3010, 0x0088)
+#define DCM_TreatmentSiteModifierCodeSequence    DcmTagKey(0x3010, 0x0089)
+#define DCM_RoboticBaseLocationIndicator         DcmTagKey(0x3010, 0x0090)
+#define DCM_RoboticPathNodeSetCodeSequence       DcmTagKey(0x3010, 0x0091)
+#define DCM_RoboticNodeIdentifier                DcmTagKey(0x3010, 0x0092)
+#define DCM_RTTreatmentSourceCoordinates         DcmTagKey(0x3010, 0x0093)
+#define DCM_RadiationSourceCoordinateSystemYawAngle DcmTagKey(0x3010, 0x0094)
+#define DCM_RadiationSourceCoordinateSystemRollAngle DcmTagKey(0x3010, 0x0095)
+#define DCM_RadiationSourceCoordinateSystemPitchAngle DcmTagKey(0x3010, 0x0096)
+#define DCM_RoboticPathControlPointSequence      DcmTagKey(0x3010, 0x0097)
+#define DCM_TomotherapeuticControlPointSequence  DcmTagKey(0x3010, 0x0098)
+#define DCM_TomotherapeuticLeafOpenDurations     DcmTagKey(0x3010, 0x0099)
+#define DCM_TomotherapeuticLeafInitialClosedDurations DcmTagKey(0x3010, 0x009a)
 #define DCM_RETIRED_Arbitrary                    DcmTagKey(0x4000, 0x0010)
 #define DCM_RETIRED_TextComments                 DcmTagKey(0x4000, 0x4000)
 #define DCM_RETIRED_ResultsID                    DcmTagKey(0x4008, 0x0040)
 #define DCM_RouteSegmentEndTime                  DcmTagKey(0x4010, 0x1026)
 #define DCM_TDRType                              DcmTagKey(0x4010, 0x1027)
 #define DCM_InternationalRouteSegment            DcmTagKey(0x4010, 0x1028)
-#define DCM_ThreatDetectionAlgorithmandVersion   DcmTagKey(0x4010, 0x1029)
+#define DCM_ThreatDetectionAlgorithmAndVersion   DcmTagKey(0x4010, 0x1029)
 #define DCM_AssignedLocation                     DcmTagKey(0x4010, 0x102a)
 #define DCM_AlarmDecisionTime                    DcmTagKey(0x4010, 0x102b)
 #define DCM_AlarmDecision                        DcmTagKey(0x4010, 0x1031)
index 87b8a5a2b11a4dba0c4612db8c421d9de3c05c42..1aeff051729a190acbc812298d817e589716ce99 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -721,7 +721,7 @@ class DCMTK_DCMDATA_EXPORT DcmElement
      *  which must be large enough to contain a complete frame.
      *  @param dataset pointer to DICOM dataset in which this pixel data object is
      *    located. Used to access rows, columns, samples per pixel etc.
-     *  @param frameNo numer of frame, starting with 0 for the first frame.
+     *  @param frameNo number of frame, starting with 0 for the first frame.
      *  @param startFragment index of the compressed fragment that contains
      *    all or the first part of the compressed bitstream for the given frameNo.
      *    Upon successful return this parameter is updated to contain the index
@@ -882,7 +882,7 @@ class DCMTK_DCMDATA_EXPORT DcmElement
   protected:
 
     /** This function returns this element's value. The returned value corresponds to the
-    *   byte ordering (little or big endian) that was passed.
+     *   byte ordering (little or big endian) that was passed.
      *  @param newByteOrder The byte ordering that shall be accounted
      *                      for (little or big endian).
      */
index cb71d1a0dfcd5801cdfb9bd990ff12d81919b27c..ab13bad6c6624d0edd6e6ebe1a760d1ae2042dc7 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -72,6 +72,7 @@ const unsigned short OFM_dcmfg    = 31;
 const unsigned short OFM_dcmtract = 32;
 const unsigned short OFM_dcmpmap  = 33;
 const unsigned short OFM_dcmelekt = 34;
+const unsigned short OFM_dcmect   = 35;
 
 // condition constants
 
@@ -170,6 +171,11 @@ extern DCMTK_DCMDATA_EXPORT const OFConditionConst EC_VOI_LUT_OBOW;
 extern DCMTK_DCMDATA_EXPORT const OFConditionConst EC_PixelDataExplLengthIllegal;
 /// Element length is larger than 32-bit length field permits
 extern DCMTK_DCMDATA_EXPORT const OFConditionConst EC_ElemLengthExceeds32BitField;
+/// Cannot write 'nan' or 'inf' as JSON number
+extern DCMTK_DCMDATA_EXPORT const OFConditionConst EC_CannotWriteJsonNumber;
+/// Cannot write compressed pixel data JSON InlineBinary
+extern DCMTK_DCMDATA_EXPORT const OFConditionConst EC_CannotWriteJsonInlineBinary;
+
 //@}
 
 // status code constants
index c8338364aa785e37add14dc8415eec03fc54e9ce..a95a46284b9c5bd40ece0453958c9e8302b87a63 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -128,11 +128,13 @@ class DCMTK_DCMDATA_EXPORT DcmFileFormat
     /** make sure that all data elements of the file meta information header are existent
      *  in metainfo and contain correct values.
      *  @param oxfer the transfer syntax which shall be used
-     *  @param writeMode flag indicating whether to update the file meta information or not
+     *  @param writeMode flag indicating whether to update the file meta information or not.
+     *         The default behavior is to delete all old meta information in order to create
+     *         it from scratch.
      *  @return EC_Normal if valid, an error code otherwise
      */
     virtual OFCondition validateMetaInfo(const E_TransferSyntax oxfer,
-                                         const E_FileWriteMode writeMode = EWM_fileformat);
+                                         const E_FileWriteMode writeMode = EWM_createNewMeta);
 
     /** get file meta information header part of the fileformat
      *  @return reference to internally stored file meta information header
@@ -221,6 +223,8 @@ class DCMTK_DCMDATA_EXPORT DcmFileFormat
      *    DcmFileFormat to the DcmDataset object.
      *  @param writeMode write file with or without meta header. Also allows for
      *    updating the information in the file meta information header.
+     *    The default behavior is to delete all old meta information in order to
+     *    create it from scratch.
      *  @return status, EC_Normal if successful, an error code otherwise
      */
     virtual OFCondition write(DcmOutputStream &outStream,
@@ -232,7 +236,7 @@ class DCMTK_DCMDATA_EXPORT DcmFileFormat
                               const Uint32 padlen = 0,
                               const Uint32 subPadlen = 0,
                               Uint32 instanceLength = 0,
-                              const E_FileWriteMode writeMode = EWM_fileformat);
+                              const E_FileWriteMode writeMode = EWM_createNewMeta);
 
     /** write object in XML format.
      *  The XML declaration (e.g. <?xml version="1.0"?>) is not written by this function.
@@ -251,20 +255,6 @@ class DCMTK_DCMDATA_EXPORT DcmFileFormat
     virtual OFCondition writeJson(STD_NAMESPACE ostream &out,
                                   DcmJsonFormat &format);
 
-    /** write object in JSON format.
-     *  @tparam Format the formatter class, e.g. DcmJsonFormatPretty.
-     *    Will be deduced automatically.
-     *  @param out output stream to which the JSON document is written
-     *  @param format used to format and customize the output
-     *  @return status, EC_Normal if successful, an error code otherwise
-     */
-    template<typename Format>
-    OFCondition writeJson(STD_NAMESPACE ostream &out,
-                          Format format)
-    {
-        return writeJson(out, OFstatic_cast(DcmJsonFormat&, format));
-    }
-
     /** load object from a DICOM file.
      *  This method supports DICOM objects stored as a file (with meta header) or as a
      *  dataset (without meta header).  By default, the presence of a meta header is
@@ -323,7 +313,9 @@ class DCMTK_DCMDATA_EXPORT DcmFileFormat
      *  @param padLength number of bytes used for the dataset padding (has to be an even number)
      *  @param subPadLength number of bytes used for the item padding (has to be an even number)
      *  @param writeMode write file with or without meta header. Also allows for updating the
-     *    information in the file meta information header.
+     *    information in the file meta information header. The default behavior is to delete
+     *    all old meta information in order to create it from scratch.
+     *
      *  @return status, EC_Normal if successful, an error code otherwise
      */
     virtual OFCondition saveFile(const OFFilename &fileName,
@@ -333,7 +325,7 @@ class DCMTK_DCMDATA_EXPORT DcmFileFormat
                                  const E_PaddingEncoding padEncoding = EPD_noChange,
                                  const Uint32 padLength = 0,
                                  const Uint32 subPadLength = 0,
-                                 const E_FileWriteMode writeMode = EWM_fileformat);
+                                 const E_FileWriteMode writeMode = EWM_createNewMeta);
 
     // methods for different pixel representations
 
index 5a4afc4f1ed14f8edde52361e9f81b13e501ef04..eaa222c2817c1a0053ffa4b3bc444352cbb868c2 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -175,21 +175,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                        const char *pixelFileName = NULL,
                        size_t *pixelCounter = NULL);
 
-    /** calculate the length of this DICOM element when encoded with the
-     *  given transfer syntax and the given encoding type for sequences.
-     *  For elements, the length includes the length of the tag, length field,
-     *  VR field and the value itself, for items and sequences it returns
-     *  the length of the complete item or sequence including delimitation tags
-     *  if applicable.
-     *  If length encoding is set to be explicit and the total item size is
-     *  larger than the available 32-bit length field, then undefined length
-     *  is returned. If "dcmWriteOversizedSeqsAndItemsImplicit" is disabled,
-     *  also the internal DcmObject errorFlag is set to EC_SeqOrItemContentOverflow
-     *  in case the item content (excluding tag header etc.) is already too
-     *  large.
-     *  @param xfer transfer syntax for length calculation
-     *  @param enctype sequence encoding type for length calculation
-     *  @return length of DICOM element
+    /** @copydoc DcmObject::calcElementLength()
      */
     virtual Uint32 calcElementLength(const E_TransferSyntax xfer,
                                      const E_EncodingType enctype);
@@ -301,6 +287,19 @@ class DCMTK_DCMDATA_EXPORT DcmItem
     virtual OFCondition writeJson(STD_NAMESPACE ostream &out,
                                   DcmJsonFormat &format);
 
+    /** write object in JSON format and control whether the output
+     *  is encapsulated in braces
+     *  @param out output stream to which the JSON document is written
+     *  @param format used to format and customize the output
+     *  @param printBraces true if output should be encapsulated in braces
+     *  @param printNewline true if a newline should be printed after a closing brace
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition writeJsonExt(STD_NAMESPACE ostream &out,
+                                  DcmJsonFormat &format,
+                                  OFBool printBraces,
+                                  OFBool printNewline);
+
     /** special write method for creation of digital signatures
      *  @param outStream DICOM output stream
      *  @param oxfer output transfer syntax
@@ -560,7 +559,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
      *                        will be handled.
      *  @param padlen         The length up to which the dataset shall be padded,
      *                        if padding is desired.
-     *  @param subPadlen      For sequences (ie sub elements), the length up to
+     *  @param subPadlen      For sequences (i.e. sub elements), the length up to
      *                        which item shall be padded, if padding is desired.
      *  @param instanceLength Number of extra bytes added to the item/dataset
      *                        length used when computing the padding; this
@@ -625,7 +624,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
 
     /** find element and get value as a reference to a C string. NB: The string is not copied!
      *  Applicable to the following VRs: AE, AS, CS, DA, DS, DT, IS, LO, LT, PN, SH, ST, TM, UC, UI,
-     *  UR, UT
+     *  UR, UT.
      *  Since the getString() routine is called internally the resulting string reference represents
      *  the (possibly multi-valued) value as stored in the dataset, i.e. no normalization is performed.
      *  The result variable 'value' is automatically set to NULL if an error occurs.
@@ -640,7 +639,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
 
     /** find element and get value as a reference to a C string. NB: The string is not copied!
      *  Applicable to the following VRs: AE, AS, CS, DA, DS, DT, IS, LO, LT, PN, SH, ST, TM, UC, UI,
-     *  UR, UT
+     *  UR, UT.
      *  Since the getString() routine is called internally the resulting string reference represents
      *  the (possibly multi-valued) value as stored in the dataset, i.e. no normalization is performed.
      *  The result variable 'value' is automatically set to NULL and 'length' is set to 0 if an error
@@ -660,7 +659,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
 
     /** find element and get value as a C++ string (only one component).
      *  Applicable to the following VRs: AE, AS, AT, CS, DA, DS, DT, FL, FD, IS, LO, LT, OB, OD, OF,
-     *  OL, OW, PN, SH, SL, SS, ST, TM, UC, UI, UL, UR, US, UT
+     *  OL, OV, OW, PN, SH, SL, SS, ST, SV, TM, UC, UI, UL, UR, US, UT, UV.
      *  Since the getOFString() routine is called internally the resulting string is normalized, i.e.
      *  leading and/or trailing spaces are removed according to the associated value representation,
      *  or the element value is converted to a character string (for non-string VRs) - see documentation
@@ -681,7 +680,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
 
     /** find element and get value as a C++ string (all components).
      *  Applicable to the following VRs: AE, AS, AT, CS, DA, DS, DT, FL, FD, IS, LO, LT, OB, OD, OF,
-     *  OL, OW, PN, SH, SL, SS, ST, TM, UC, UI, UL, UR, US, UT
+     *  OL, OV, OW, PN, SH, SL, SS, ST, SV, TM, UC, UI, UL, UR, US, UT, UV.
      *  Since the getOFStringArray() routine is called internally the resulting string is normalized,
      *  i.e. leading and/or trailing spaces are removed according to the associated value representation
      *  or the element values are converted to character strings (for non-string VRs) - see documentation
@@ -697,7 +696,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                         const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as an unsigned 8-bit integer.
-     *  Applicable to the following VRs: OB
+     *  Applicable to the following VRs: OB.
      *  The result variable 'value' is automatically set to zero if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the element value is stored
@@ -711,7 +710,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                 const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as an array of unsigned 8-bit integers.
-     *  Applicable to the following VRs: OB
+     *  Applicable to the following VRs: OB.
      *  The result variable 'value' is automatically set to NULL if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the reference to the element value is stored
@@ -725,7 +724,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                      const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as an unsigned 16-bit integer.
-     *  Applicable to the following VRs: OW, US
+     *  Applicable to the following VRs: OW, US.
      *  The result variable 'value' is automatically set to zero if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the element value is stored
@@ -739,7 +738,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                  const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as an array of unsigned 16-bit integers.
-     *  Applicable to the following VRs: AT, OW, US
+     *  Applicable to the following VRs: AT, OW, US.
      *  The result variable 'value' is automatically set to NULL if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the reference to the element value is stored
@@ -753,7 +752,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                       const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as a signed 16-bit integer.
-     *  Applicable to the following VRs: SS
+     *  Applicable to the following VRs: SS.
      *  The result variable 'value' is automatically set to zero if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the element value is stored
@@ -767,7 +766,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                  const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as an array of signed 16-bit integers.
-     *  Applicable to the following VRs: SS
+     *  Applicable to the following VRs: SS.
      *  The result variable 'value' is automatically set to NULL if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the reference to the element value is stored
@@ -781,7 +780,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                       const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as an unsigned 32-bit integer.
-     *  Applicable to the following VRs: OL, UL
+     *  Applicable to the following VRs: OL, UL.
      *  The result variable 'value' is automatically set to zero if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the element value is stored
@@ -795,7 +794,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                  const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as an array of unsigned 32-bit integers.
-     *  Applicable to the following VRs: OL, UL
+     *  Applicable to the following VRs: OL, UL.
      *  The result variable 'value' is automatically set to NULL if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the reference to the element value is stored
@@ -809,7 +808,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                       const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as a signed 32-bit integer.
-     *  Applicable to the following VRs: IS, SL
+     *  Applicable to the following VRs: IS, SL.
      *  The result variable 'value' is automatically set to zero if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the element value is stored
@@ -823,7 +822,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                  const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as an array of signed 32-bit integers.
-     *  Applicable to the following VRs: SL
+     *  Applicable to the following VRs: SL.
      *  The result variable 'value' is automatically set to NULL if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the reference to the element value is stored
@@ -837,7 +836,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                       const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as an unsigned 64-bit integer.
-     *  Applicable to the following VRs: OV, UV
+     *  Applicable to the following VRs: OV, UV.
      *  The result variable 'value' is automatically set to zero if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the element value is stored
@@ -851,7 +850,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                  const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as an array of unsigned 64-bit integers.
-     *  Applicable to the following VRs: OV, UV
+     *  Applicable to the following VRs: OV, UV.
      *  The result variable 'value' is automatically set to NULL if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the reference to the element value is stored
@@ -865,7 +864,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                       const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as a signed 64-bit integer.
-     *  Applicable to the following VRs: SV
+     *  Applicable to the following VRs: SV.
      *  The result variable 'value' is automatically set to zero if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the element value is stored
@@ -879,7 +878,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                  const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as an array of signed 64-bit integers.
-     *  Applicable to the following VRs: SV
+     *  Applicable to the following VRs: SV.
      *  The result variable 'value' is automatically set to NULL if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the reference to the element value is stored
@@ -893,7 +892,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                       const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as a (signed) long integer.
-     *  Applicable to the following VRs: IS, OL, SL, SS, UL, US
+     *  Applicable to the following VRs: IS, OL, SL, SS, UL, US.
      *  The result variable 'value' is automatically set to zero if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the element value is stored
@@ -907,7 +906,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                   const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as a 32-bit floating point.
-     *  Applicable to the following VRs: FL, OF
+     *  Applicable to the following VRs: FL, OF.
      *  The result variable 'value' is automatically set to zero if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the element value is stored
@@ -921,7 +920,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                   const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as an array of 32-bit floating point values.
-     *  Applicable to the following VRs: FL, OF
+     *  Applicable to the following VRs: FL, OF.
      *  The result variable 'value' is automatically set to NULL if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the reference to the element value is stored
@@ -935,7 +934,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                        const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as a 64-bit floating point.
-     *  Applicable to the following VRs: DS, FD, OD
+     *  Applicable to the following VRs: DS, FD, OD.
      *  The result variable 'value' is automatically set to zero if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the element value is stored
@@ -949,7 +948,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                   const OFBool searchIntoSub = OFFalse);
 
     /** find element and get value as an array of 64-bit floating point values.
-     *  Applicable to the following VRs: FD, OD
+     *  Applicable to the following VRs: FD, OD.
      *  The result variable 'value' is automatically set to NULL if an error occurs.
      *  @param tagKey DICOM tag specifying the attribute to be searched for
      *  @param value variable in which the reference to the element value is stored
@@ -963,7 +962,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                        const OFBool searchIntoSub = OFFalse);
 
     /** looks up and returns a given sequence.
-     *  Applicable to the following VRs: SQ, (pixelSQ)
+     *  Applicable to the following VRs: SQ, (pixelSQ).
      *  The result variable 'sequence' is automatically set to NULL if an error occurs
      *  (e.g. if 'seqTagKey' does not refer to a sequence attribute).
      *  @param seqTagKey DICOM tag specifying the sequence attribute to be searched for
@@ -981,7 +980,8 @@ class DCMTK_DCMDATA_EXPORT DcmItem
      *  to NULL and returns EC_TagNotFound (specified sequence does not exist) or
      *  EC_IllegalParameter (specified item does not exist). Only the top-most level of
      *  the dataset/item is examined (i.e. no deep-search is performed).
-     *  Applicable to the following VRs: SQ, (pixelSQ)
+     *  Applicable to the following VRs: SQ, (pixelSQ).
+     *  Please note that an instance of the DcmPixelItem class cannot be retrieved.
      *  @param seqTagKey DICOM tag specifying the sequence attribute to be searched for
      *  @param item variable in which the reference to (or copy of) the item is stored
      *  @param itemNum number of the item to be searched for (0..n-1, -1 for last)
@@ -1000,7 +1000,9 @@ class DCMTK_DCMDATA_EXPORT DcmItem
      *  If either the sequence or the item do not exist, they are created. If necessary,
      *  multiple empty items are inserted. Only the top-most level of the dataset/item
      *  is examined (i.e. no deep-search is performed).
-     *  Applicable to the following VRs: SQ, (pixelSQ)
+     *  Applicable to the following VRs: SQ, (pixelSQ).
+     *  Please note that an instance of the DcmPixelItem class cannot be retrieved or
+     *  created.
      *  @param seqTag DICOM tag specifying the sequence attribute to be searched for
      *    (or to be created)
      *  @param item variable in which the reference to the sequence item is stored
@@ -1042,7 +1044,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                      const OFBool searchIntoSub = OFFalse);
 
     /** looks up the given sequence in the current dataset and deletes the given item.
-     *  Applicable to the following VRs: SQ, (pixelSQ)
+     *  Applicable to the following VRs: SQ, (pixelSQ).
      *  @param seqTagKey DICOM tag specifying the sequence attribute to be searched for
      *  @param itemNum number of the item to be deleted (0..n-1, -1 for last)
      *  @return EC_Normal upon success, an error otherwise.
@@ -1055,7 +1057,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
 
     /** create a new element, put specified value to it and insert the element into the dataset/item.
      *  Applicable to the following VRs: AE, AS, AT, CS, DA, DS, DT, FL, FD, IS, LO, LT, OB, OD, OF,
-     *  OL, OW, PN, SH, SL, SS, ST, TM, UC, UI, UL, UR, US, UT
+     *  OL, OV, OW, PN, SH, SL, SS, ST, SV, TM, UC, UI, UL, UR, US, UT, UV.
      *  @param tag DICOM tag specifying the attribute to be created
      *  @param value string value to be set for the new element (might be empty or NULL)
      *  @param replaceOld flag indicating whether to replace an existing element or not
@@ -1067,7 +1069,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
 
     /** create a new element, put specified value to it and insert the element into the dataset/item.
      *  Applicable to the following VRs: AE, AS, AT, CS, DA, DS, DT, FL, FD, IS, LO, LT, OB, OD, OF,
-     *  OL, OW, PN, SH, SL, SS, ST, TM, UC, UI, UL, UR, US, UT
+     *  OL, OV, OW, PN, SH, SL, SS, ST, SV, TM, UC, UI, UL, UR, US, UT, UV.
      *  Please note that since the length of the string has to be specified explicitly, the string
      *  can contain more than one NULL byte.
      *  @param tag DICOM tag specifying the attribute to be created
@@ -1082,8 +1084,8 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                    const OFBool replaceOld = OFTrue);
 
     /** create a new element, put specified value to it and insert the element into the dataset/item.
-     *  Applicable to the following VRs: AE, AS, CS, DA, DS, DT, IS, LO, LT, PN, SH, ST, TM, UC, UI,
-     *  UR, UT
+     *  Applicable to the following VRs: AE, AS, AT, CS, DA, DS, DT, FL, FD, IS, LO, LT, OB, OD, OF,
+     *  OL, OV, OW, PN, SH, SL, SS, ST, SV, TM, UC, UI, UL, UR, US, UT, UV.
      *  @param tag DICOM tag specifying the attribute to be created
      *  @param value value to be set for the new element (might be empty)
      *  @param replaceOld flag indicating whether to replace an existing element or not
@@ -1094,7 +1096,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                           const OFBool replaceOld = OFTrue);
 
     /** create a new element, put specified value to it and insert the element into the dataset/item.
-     *  Applicable to the following VRs: OB, ox (polymorph OB/OW or pixel data)
+     *  Applicable to the following VRs: OB, ox (polymorph OB/OW or pixel data).
      *  @param tag DICOM tag specifying the attribute to be created
      *  @param value value to be set for the new element (might be NULL)
      *  @param count number of values (= bytes in this case) to be copied from 'value'
@@ -1107,7 +1109,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                        const OFBool replaceOld = OFTrue);
 
     /** create a new element, put specified value to it and insert the element into the dataset/item.
-     *  Applicable to the following VRs: US, xs (US or SS)
+     *  Applicable to the following VRs: US, xs (US or SS).
      *  @param tag DICOM tag specifying the attribute to be created
      *  @param value value to be set for the new element
      *  @param pos index of the value to be set (0..vm). A value can be appended to
@@ -1121,7 +1123,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                    const OFBool replaceOld = OFTrue);
 
     /** create a new element, put specified value to it and insert the element into the dataset/item.
-     *  Applicable to the following VRs: AT, OW, US, ox (polymorph OB/OW or pixel data), xs (US or SS)
+     *  Applicable to the following VRs: AT, OW, US, ox (polymorph OB/OW or pixel data), xs (US or SS).
      *  @param tag DICOM tag specifying the attribute to be created
      *  @param value value to be set for the new element (might be NULL)
      *  @param count number of values (not bytes!) to be copied from 'value'
@@ -1134,7 +1136,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                         const OFBool replaceOld = OFTrue);
 
     /** create a new element, put specified value to it and insert the element into the dataset/item.
-     *  Applicable to the following VRs: SS, xs (US or SS)
+     *  Applicable to the following VRs: SS, xs (US or SS).
      *  @param tag DICOM tag specifying the attribute to be created
      *  @param value value to be set for the new element
      *  @param pos index of the value to be set (0..vm). A value can be appended to
@@ -1148,7 +1150,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                    const OFBool replaceOld = OFTrue);
 
     /** create a new element, put specified value to it and insert the element into the dataset/item.
-     *  Applicable to the following VRs: SS, xs (US or SS)
+     *  Applicable to the following VRs: SS, xs (US or SS).
      *  @param tag DICOM tag specifying the attribute to be created
      *  @param value value to be set for the new element
      *  @param count number of values (not bytes!) to be copied from 'value'
@@ -1161,7 +1163,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                         const OFBool replaceOld = OFTrue);
 
     /** create a new element, put specified value to it and insert the element into the dataset/item.
-     *  Applicable to the following VRs: OL, UL
+     *  Applicable to the following VRs: OL, UL.
      *  @param tag DICOM tag specifying the attribute to be created
      *  @param value value to be set for the new element
      *  @param pos index of the value to be set (0..vm). A value can be appended to
@@ -1175,7 +1177,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                    const OFBool replaceOld = OFTrue);
 
     /** create a new element, put specified value to it and insert the element into the dataset/item.
-     *  Applicable to the following VRs: OL, UL
+     *  Applicable to the following VRs: OL, UL.
      *  @param tag DICOM tag specifying the attribute to be created
      *  @param value value to be set for the new element
      *  @param count number of values (not bytes!) to be copied from 'value'
@@ -1188,7 +1190,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                        const OFBool replaceOld = OFTrue);
 
     /** create a new element, put specified value to it and insert the element into the dataset/item.
-     *  Applicable to the following VRs: SL
+     *  Applicable to the following VRs: SL.
      *  @param tag DICOM tag specifying the attribute to be created
      *  @param value value to be set for the new element
      *  @param pos index of the value to be set (0..vm). A value can be appended to
@@ -1202,7 +1204,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                    const OFBool replaceOld = OFTrue);
 
     /** create a new element, put specified value to it and insert the element into the dataset/item.
-     *  Applicable to the following VRs: FL, OF
+     *  Applicable to the following VRs: FL, OF.
      *  @param tag DICOM tag specifying the attribute to be created
      *  @param value value to be set for the new element
      *  @param pos index of the value to be set (0..vm). A value can be appended to
@@ -1216,7 +1218,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                     const OFBool replaceOld = OFTrue);
 
     /** create a new element, put specified value to it and insert the element into the dataset/item.
-     *  Applicable to the following VRs: FL, OF
+     *  Applicable to the following VRs: FL, OF.
      *  @param tag DICOM tag specifying the attribute to be created
      *  @param value value to be set for the new element
      *  @param count number of values (not bytes!) to be copied from 'value'
@@ -1229,7 +1231,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                          const OFBool replaceOld = OFTrue);
 
     /** create a new element, put specified value to it and insert the element into the dataset/item.
-     *  Applicable to the following VRs: FD, OD
+     *  Applicable to the following VRs: DS, FD, OD
      *  @param tag DICOM tag specifying the attribute to be created
      *  @param value value to be set for the new element
      *  @param pos index of the value to be set (0..vm). A value can be appended to
@@ -1243,7 +1245,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                     const OFBool replaceOld = OFTrue);
 
     /** create a new element, put specified value to it and insert the element into the dataset/item.
-     *  Applicable to the following VRs: FD, OD
+     *  Applicable to the following VRs: FD, OD.
      *  @param tag DICOM tag specifying the attribute to be created
      *  @param value value to be set for the new element
      *  @param count number of values (not bytes!) to be copied from 'value'
@@ -1256,7 +1258,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
                                          const OFBool replaceOld = OFTrue);
 
     /** create a new element, put specified value to it and insert the element into the dataset/item.
-     *  Applicable to the following VRs: AT
+     *  Applicable to the following VRs: AT.
      *  @param tag DICOM tag specifying the attribute to be created
      *  @param value value to be set for the new element
      *  @param pos index of the value to be set (0..vm). A value can be appended to
@@ -1273,7 +1275,7 @@ class DCMTK_DCMDATA_EXPORT DcmItem
 
     /** create a new element (with no value) and insert it into the dataset/item.
      *  Applicable to the following VRs: AE, AS, AT, CS, DA, DS, DT, FL, FD, IS, LO, LT, OB, OD, OF,
-     *  OL, OW, PN, SH, SL, SQ, SS, ST, TM, UC, UI, UL, UR, US, UT
+     *  OL, OV, OW, PN, SH, SL, SQ, SS, ST, SV, TM, UC, UI, UL, UR, US, UT, UV.
      *  @param tag DICOM tag specifying the attribute to be created
      *  @param replaceOld flag indicating whether to replace an existing element or not
      *  @return EC_Normal upon success, an error code otherwise.
@@ -1285,7 +1287,8 @@ class DCMTK_DCMDATA_EXPORT DcmItem
      *  If the sequence does not exist, it is created. If necessary, multiple empty items
      *  are inserted before the specified item position. Only the top-most level of the
      *  dataset/item is examined (i.e. no deep-search is performed).
-     *  Applicable to the following VRs: SQ, (pixelSQ)
+     *  Applicable to the following VRs: SQ, (pixelSQ).
+     *  Please note that an instance of the DcmPixelItem class cannot be inserted.
      *  @param seqTag DICOM tag specifying the sequence attribute to be searched for
      *    (or to be created)
      *  @param item item to be inserted into the sequence, must not be contained in this
index d60b18e041072a3e3c87ed4b3e627da1cd212cff..d501dcc88411b794ccdc3997a191caddb7107d95 100644 (file)
@@ -1,6 +1,6 @@
 /*
 *
-*  Copyright (C) 2017-2018, OFFIS e.V.
+*  Copyright (C) 2017-2020, OFFIS e.V.
 *  All rights reserved.  See COPYRIGHT file for details.
 *
 *  This software and supporting documentation were developed by
@@ -200,6 +200,7 @@ public:
      */
     inline DcmJsonFormat(const OFBool printMetaInfo)
     : printMetaheaderInformation(printMetaInfo)
+    , enableJsonExtension(OFFalse)
     {
 
     }
@@ -313,6 +314,21 @@ public:
      */
     virtual void printNextArrayElementPrefix(STD_NAMESPACE ostream &out);
 
+    /** return the flag indicating whether extended JSON number encoding is enabled.
+     */
+    virtual OFBool getJsonExtensionEnabled() const
+    {
+      return enableJsonExtension;
+    }
+
+    /** set the flag indicating whether extended JSON number encoding is enabled.
+     *  @param enabled new value of the flag
+     */
+    virtual void setJsonExtensionEnabled(OFBool enabled)
+    {
+      enableJsonExtension = enabled;
+    }
+
     /** Option that defines if metaheader information should be printed.
      */
     const OFBool printMetaheaderInformation;
@@ -330,6 +346,16 @@ protected:
     /** Used for decreasing the indention level.
      */
     virtual void decreaseIndention() = 0;
+
+private:
+
+    /** Option that defines if the inofficial JSON extension should be
+     *  permitted under which decimal numbers may have the values "-inf",
+     *  "inf" or "nan". Default is OFFalse, in which case such values
+     *  will lead to an error code being returned instead.
+     */
+    OFBool enableJsonExtension;
+
 };
 
 
@@ -339,7 +365,7 @@ protected:
 class DCMTK_DCMDATA_EXPORT DcmJsonFormatPretty : public DcmJsonFormat
 {
 private:
-    /** Variable for the indentenlevel of DcmJsonFormat
+    /** Variable for the indention level of DcmJsonFormat
      */
     unsigned m_IndentionLevel;
 
index c0d5a68325051ff5f83ecc62532db746148a46f2..b62eacfa31b2864a25eb27dbeddad41a2680e71f 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -436,6 +436,18 @@ class DCMTK_DCMDATA_EXPORT DcmObject
      *    actually represent a compound value (e.g. items like DcmPixelItem).
      *    Such overflows will be detected, in which case the maximum possible
      *    value will be returned instead, coinciding with DCM_UndefinedLength.
+     *  @warning The implementation in DcmPixelData may return zero if no
+     *    conforming representation exists and set the
+     *    EC_RepresentationNotFound error flag to indicated it.
+     *  @warning When calculation the length of a sequence or an item
+     *    containing multiple attributes, the implementation may return
+     *    DCM_UndefinedLength to indicate a value that can not be encoded as
+     *    a 32 bit length field. It will even do so if
+     *    "dcmWriteOversizedSeqsAndItemsUndefined" is disabled, but then also
+     *    set the EC_SeqOrItemContentOverflow error flag (inside getLength())
+     *    to indicated it.
+     *  @note Just check for zero or DCM_UndefinedLength return value and then
+     *    have a look at the error flag in either case.
      *  @param xfer transfer syntax for length calculation
      *  @param enctype sequence encoding type for length calculation
      *  @return length of DICOM element
index fe229f384aae00bc5675096e566623bc73d39d21..1d864951ace3f51b3fd7d59ae352e871f5e3ca09 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2008-2017, OFFIS e.V.
+ *  Copyright (C) 2008-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #ifndef DCPATH_H
 #define DCPATH_H
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 
 #include "dcmtk/dcmdata/dcdatset.h"
 
-
 /** Class representing a node in DcmPath. A node contains just
 * a pointer to a DcmObject (e.g. a sequence or an item). Additionally
 * an item number is stored which also makes sense in case that the
 * object pointed to is an item. The item number is necessary because
 * when having only a pointer to a DcmItem there is no way to find out
 * at which position the item actually has in the surrounding sequence.
 */
+ * a pointer to a DcmObject (e.g. a sequence or an item). Additionally
+ * an item number is stored which also makes sense in case that the
+ * object pointed to is an item. The item number is necessary because
+ * when having only a pointer to a DcmItem there is no way to find out
+ * at which position the item actually has in the surrounding sequence.
+ */
 class DCMTK_DCMDATA_EXPORT DcmPathNode
 {
 
 public:
-
-  /** Constructor. Creates empty path node.
-   */
-  DcmPathNode() : m_obj(NULL), m_itemNo(0) {}
-
-  /** Constructor. Creates search node from object pointer and item number.
-   *  @param obj [in] The object the search node points to. The memory of the
-   *             given DICOM object is not handled by the node itself but
-   *             must be handled (i.e. freed) from outside.
-   *  @param itemNo [in] The item number that should be set. Only relevant
-   *                if obj parameter contains an item
-   */
-  DcmPathNode(DcmObject* obj, Uint32 itemNo)    : m_obj(obj), m_itemNo(itemNo) {}
-
-  /** Destructor. Nothing to do, the DICOM object is not freed automatically!
-   */
-  ~DcmPathNode() { }
-
-  /// Pointer to object this search node points to
-  DcmObject* m_obj;
-
-  /// The item number of the item in m_obj; only useful if m_obj is an item
-  Uint32 m_itemNo;
+    /** Constructor. Creates empty path node.
+     */
+    DcmPathNode()
+        : m_obj(NULL)
+        , m_itemNo(0)
+    {
+    }
+
+    /** Constructor. Creates search node from object pointer and item number.
+     *  @param obj [in] The object the search node points to. The memory of the
+     *             given DICOM object is not handled by the node itself but
+     *             must be handled (i.e. freed) from outside.
+     *  @param itemNo [in] The item number that should be set. Only relevant
+     *                if obj parameter contains an item
+     */
+    DcmPathNode(DcmObject* obj, Uint32 itemNo)
+        : m_obj(obj)
+        , m_itemNo(itemNo)
+    {
+    }
+
+    /** Destructor. Nothing to do, the DICOM object is not freed automatically!
+     */
+    ~DcmPathNode()
+    {
+    }
+
+    /// Pointer to object this search node points to
+    DcmObject* m_obj;
+
+    /// The item number of the item in m_obj; only useful if m_obj is an item
+    Uint32 m_itemNo;
 
 private:
-
-  /** Private undefined copy constructor
-   */
-  DcmPathNode(const DcmPathNode& rhs);
-
-  /** Private undefined assignment operator
-   */
-  DcmPathNode& operator=(const DcmPathNode& arg);
+    /** Private undefined copy constructor
+     *  @param rhs Object to copy from
+     */
+    DcmPathNode(const DcmPathNode& rhs);
+
+    /** Private undefined assignment operator
+     *  @param arg Object to copy from
+     *  @return Reference to this object
+     */
+    DcmPathNode& operator=(const DcmPathNode& arg);
 };
 
-
 /** Class representing a path of DICOM objects. A path is a "way" through
  *  a DICOM dataset, i.e. it starts e.g. with an item, followed by a sequence
  *  originally contained in this item. The sequence then could be followed by
@@ -86,434 +95,429 @@ class DCMTK_DCMDATA_EXPORT DcmPath
 {
 
 public:
-
-  /** Constructor, creates an empty search result
-   */
-  DcmPath();
-
-  /** Constructor, creates a search result from a list of search nodes.
-   *  @param currentPath [in] The list of search nodes representing a
-   *                     "path" through a DICOM dataset
-   */
-  DcmPath(const OFList<DcmPathNode*>& currentPath);
-
-  /** Appends a search node at the end of the search result path. It is not
-   *  checked whether the resulting path is still valid.
-   *  @param node [in] The node to append.
-   *
-   */
-  void append(DcmPathNode* node);
-
-  /** Removes last path node from path. Also frees memory of path node
-   *  but does _not_ free memory of the underlying DICOM item or element.
-   *  @return none
-   */
-  void deleteBackNode();
-
-  /** Returns iterator pointing to first path component.
-   *  @return Iterator to first path node.
-   */
-  OFListIterator(DcmPathNode*) begin();
-
-  /** Returns last path component.
-   *  @return The last path component, NULL if none exists.
-   */
-  DcmPathNode* back();
-
-  /** Returns iterator pointing to last path component.
-   *  @return Iterator to last path node.
-   */
-  OFListIterator(DcmPathNode*) end();
-
-  /** Returns number of path components.
-   *  @return The number of path components
-   */
-  Uint32 size() const;
-
-  /** Returns whether path is empty, ie does not contain any path nodes
-   *  @return OFTrue, if path is empty, OFFalse otherwise
-   */
-  OFBool empty() const;
-
-  /** Returns a string representation of the path,
-   *  e.g.\ "SourceImageSequence[0].ReferencedSOPInstanceUID"
-   *  @return String representing path
-   */
-  OFString toString() const;
-
-  /** Returns whether the path contains tags of a given group.
-   *  Might be useful for looking after (unwanted) meta header tags etc.
-   *  @param groupNo [in] The group number to look for
-   *  @return OFTrue if group number is found in path, OFFalse otherwise
-   */
-  OFBool containsGroup(const Uint16 groupNo) const;
-
-  /** Returns a string representation of each path node separately.
-   *  Tags are represented as numbers surrounded by braces "(gggg,eeee)",
-   *  not dictionary names. Items are represented by a number or wildcard
-   *  in square brackets, eg. "[12]" or "[*]".
-   *  @param path The path to parse into different nodes
-   *  @param result [out] List containing the resulting strings
-   *  @return none
-   */
-  static OFCondition separatePathNodes(const OFString& path, OFList<OFString>& result);
-
-  /** Helper function for findOrCreatePath(). Parses an item number from
-   *  the beginning of the path string. The item number must be positive,
-   *  starting with 0.
-   *  The path must start like "[itemnumber]...".
-   *  @param path [in/out] The path starting with the item number in square
-   *              brackets, e.g.\ "[3]". The parsed item number and a
-   *              potentially following "." are removed from the path
-   *  @param itemNo [out] The parsed item number. If a wildcard was parsed,
-   *                this output parameter is not set at all.
-   *  @param wasWildcard [out] Is set to OFTrue, if wildcard was parsed
-   *                     (instead of concrete item number).
-   *  @return EC_Normal, if concrete item number or wildcard was parsed
-   */
-  static OFCondition parseItemNoFromPath(OFString& path,                   // inout
-                                         Uint32& itemNo,                   // out
-                                         OFBool& wasWildcard);             // out
-
-  /** Function that parses a tag from the beginning of a path string.
-   *  The tag has to be either in numeric format, e.g. "(0010,0010)" or
-   *  a dictionary name, e.g. "PatientName". If successful, the
-   *  parsed tag is removed from the path string.
-   *  @param path [in/out] The path string, starting with the attribute
-   *              to parse
-   *  @param tag [out] The tag parsed
-   *  @return EC_Normal if successful, error code otherwise
-   */
-  static OFCondition parseTagFromPath(OFString& path,         // inout
-                                      DcmTag& tag);           // out
-
-  /** Desctructor, cleans up memory of path nodes. Does not delete
-   *  the DcmObjects the nodes point to (this is also not done
-   *  by the desctructor of the path nodes, so the caller is responsible
-   *  for freeing any related DICOM objects.
-   */
-  ~DcmPath();
+    /** Constructor, creates an empty search result
+     */
+    DcmPath();
+
+    /** Constructor, creates a search result from a list of search nodes.
+     *  @param currentPath [in] The list of search nodes representing a
+     *                     "path" through a DICOM dataset
+     */
+    DcmPath(const OFList<DcmPathNode*>& currentPath);
+
+    /** Appends a search node at the end of the search result path. It is not
+     *  checked whether the resulting path is still valid.
+     *  @param node [in] The node to append.
+     *
+     */
+    void append(DcmPathNode* node);
+
+    /** Removes last path node from path. Also frees memory of path node
+     *  but does _not_ free memory of the underlying DICOM item or element.
+     *  @return none
+     */
+    void deleteBackNode();
+
+    /** Returns iterator pointing to first path component.
+     *  @return Iterator to first path node.
+     */
+    OFListIterator(DcmPathNode*) begin();
+
+    /** Returns last path component.
+     *  @return The last path component, NULL if none exists.
+     */
+    DcmPathNode* back();
+
+    /** Returns iterator pointing to last path component.
+     *  @return Iterator to last path node.
+     */
+    OFListIterator(DcmPathNode*) end();
+
+    /** Returns number of path components.
+     *  @return The number of path components
+     */
+    Uint32 size() const;
+
+    /** Returns whether path is empty, ie does not contain any path nodes
+     *  @return OFTrue, if path is empty, OFFalse otherwise
+     */
+    OFBool empty() const;
+
+    /** Returns a string representation of the path,
+     *  e.g.\ "SourceImageSequence[0].ReferencedSOPInstanceUID"
+     *  @return String representing path
+     */
+    OFString toString() const;
+
+    /** Returns whether the path contains tags of a given group.
+     *  Might be useful for looking after (unwanted) meta header tags etc.
+     *  @param groupNo [in] The group number to look for
+     *  @return OFTrue if group number is found in path, OFFalse otherwise
+     */
+    OFBool containsGroup(const Uint16 groupNo) const;
+
+    /** Returns a string representation of each path node separately.
+     *  Tags are represented as numbers surrounded by braces "(gggg,eeee)",
+     *  not dictionary names. Items are represented by a number or wildcard
+     *  in square brackets, eg. "[12]" or "[*]".
+     *  @param path The path to parse into different nodes
+     *  @param result [out] List containing the resulting strings
+     *  @return none
+     */
+    static OFCondition separatePathNodes(const OFString& path, OFList<OFString>& result);
+
+    /** Helper function for findOrCreatePath(). Parses an item number from
+     *  the beginning of the path string. The item number must be positive,
+     *  starting with 0.
+     *  The path must start like "[itemnumber]...".
+     *  @param path [in/out] The path starting with the item number in square
+     *              brackets, e.g.\ "[3]". The parsed item number and a
+     *              potentially following "." are removed from the path
+     *  @param itemNo [out] The parsed item number. If a wildcard was parsed,
+     *                this output parameter is not set at all.
+     *  @param wasWildcard [out] Is set to OFTrue, if wildcard was parsed
+     *                     (instead of concrete item number).
+     *  @return EC_Normal, if concrete item number or wildcard was parsed
+     */
+    static OFCondition parseItemNoFromPath(OFString& path,       // inout
+                                           Uint32& itemNo,       // out
+                                           OFBool& wasWildcard); // out
+
+    /** Function that parses a tag from the beginning of a path string.
+     *  The tag has to be either in numeric format, e.g. "(0010,0010)" or
+     *  a dictionary name, e.g. "PatientName". If successful, the
+     *  parsed tag is removed from the path string.
+     *  @param path [in/out] The path string, starting with the attribute
+     *              to parse
+     *  @param tag [out] The tag parsed
+     *  @return EC_Normal if successful, error code otherwise
+     */
+    static OFCondition parseTagFromPath(OFString& path, // inout
+                                        DcmTag& tag);   // out
+
+    /** Desctructor, cleans up memory of path nodes. Does not delete
+     *  the DcmObjects the nodes point to (this is also not done
+     *  by the desctructor of the path nodes, so the caller is responsible
+     *  for freeing any related DICOM objects.
+     */
+    ~DcmPath();
 
 private:
-
-  /// Internal list representing the nodes in the path.
-  OFList<DcmPathNode*> m_path;
-
-  /** Private undefined copy constructor
-   */
-  DcmPath(const DcmPath& rhs);
-
-  /** Private undefined assignment operator
-   */
-  DcmPath& operator=(const DcmPath& arg);
+    /// Internal list representing the nodes in the path.
+    OFList<DcmPathNode*> m_path;
+
+    /** Private undefined copy constructor
+     *  @param rhs Path to copy from
+     */
+    DcmPath(const DcmPath& rhs);
+
+    /** Private undefined assignment operator
+     *  @param arg Path to copy from
+     *  @return Reference to this object
+     */
+    DcmPath& operator=(const DcmPath& arg);
 };
 
-
+/// Class that operates on DICOM datasets using a (string) path syntax.
 class DCMTK_DCMDATA_EXPORT DcmPathProcessor
 {
 
 public:
-
-  /** Constructor, creates an empty search object.
-   */
-  DcmPathProcessor();
-
-  /** Sets whether searching/creating paths will support wildcard for
-   *  items. If set to false, any path operation with item wildcard characters
-   *  will return an error.
-   *  @param supported [in] If true, wildcard are enabled (default)
-   *                   If false, item wildcard support is disabled.
-   */
-  void setItemWildcardSupport(const OFBool supported);
-
-
-  /** Enables (class default: enabled) or disables checking of private
-   *  reservations when inserting private tags. If enabled and a private
-   *  tag is created that has no private reservation, an error is returned.
-   *  If disabled, it is possible to insert private tags that do not have
-   *  a reservation in the corresponding item/dataset.
-   *  @param doChecking [in] OFTrue enables reservation checking,
-   *                    OFFalse disables it.
-   */
-  void checkPrivateReservations(const OFBool doChecking);
-
-  /** Checks in item, whether a private reservation for a given
-   *  tag key exists.
-   *  @param item   [in] The item to search in
-   *  @param tagKey [in/out] The tag to be checked.
-   *  @param privateCreator [in] The private creator to check for (if known,
-   *                        can be left empty)
-   *  @return Return EC_Normal if reservation checking was successful.
-   *          Otherwise an error code is returned.
-   */
-  static OFCondition checkPrivateTagReservation(DcmItem* item,
-                                                const DcmTagKey& tagKey,
-                                                const OFString& privateCreator = "");
-
-  /** Checks in item, whether a private reservation for a given
-   *  tag key. If so, a dictionary lookup is performed and the VR and private
-   *  creator of the tag is updated correspondingly.
-   *  @param item [in] The item to search in
-   *  @param tag [in/out] The tag to be checked. Will be updated with VR and
-   *                      private creator.
-   *  @param privateCreator [in] The private creator to check for (if known,
-   *                        can be left empty)
-   *  @return Return EC_Normal if reservation checking and updating the
-   *          tag was successful. Otherwise an error code is returned.
-   */
-  static OFCondition checkPrivateTagReservation(DcmItem* item,
-                                                DcmTag& tag,
-                                                const OFString& privateCreator = "");
-
-  /** Function that allows for finding and/or inserting a hierarchy of items
-   *  and attributes as defined by a path string; also returns a list of
-   *  pointers for each successfully found or inserted paths. Every list
-   *  contains pointers pointing to all the objects along the path
-   *  starting from the object given as parameter. The pointer to the
-   *  starting object will not be part of the result.
-   *
-   *  In principle, the path string must have the following format (in
-   *  arbitrary depth). Note that for searching a sequence, the example
-   *  below would start with [ITEMNO] instead:
-   *  SEQUENCE[ITEMNO].SEQUENCE[ITEMNO].ATTRIBUTE
-   *  . ITEMNO must be a positive integer starting with 0.
-   *  SEQUENCE and ATTRIBUTE must be a tag, written e.g.
-   *  "(0010,0010)" or as a dictionary name, e.g. "PatientName". If the
-   *  path cannot be fully created (see option createIfNecessary), any
-   *  possibly object changes are reverted. So a path is either fully created
-   *  or no path component is created at all. The result can be obtained
-   *  by calling the getResults() function.
-   *
-   *  Example: The path
-   *  "ContentSequence[4].(0040,a043)[0].CodeValue" selects the Content
-   *  Sequence in the given object, therein the 5th item, therein the "Concept
-   *  Name Code Sequence" denoted by (0040,a043), therein the first item
-   *  and finally therein the tag "Code Value".
-   *  The resulting object list should (if success is returned) contain
-   *  1 result, consisting of a list with 5 pointers to 5 objects in the order
-   *  in their logical order as they occur in the path string
-   *  (in total 2 sequences, 2 items, and one leaf attribute).
-   *  @param obj [in] The object to search (or create) a path in
-   *  @param path [in] The path either starting with an attribute (either a
-   *              sequence or a leaf attribute as a dictionary name or tag) or
-   *              starting with an item
-   *  @param createIfNecessary [in] If set, all missing objects found
-   *                           in the path string are created. If not set,
-   *                           only existing paths can be accessed and
-   *                           no new attribute or item is created.
-   *  @return EC_Normal if successful, error code otherwise.
-   */
-  OFCondition findOrCreatePath(DcmObject* obj,
-                               const OFString& path,
-                               OFBool createIfNecessary = OFFalse);
-
-  /** Function that allows for deleting elements and items from
-   *  a DICOM object tree.
-   *  In principle, the path string must have the following format (in
-   *  arbitrary depth). Note that for searching in a sequence, the example
-   *  below would start with [ITEMNO] instead:
-   *  SEQUENCE[ITEMNO].SEQUENCE[ITEMNO].ATTRIBUTE
-   *  . ITEMNO must be a positive integer starting with 0.
-   *  SEQUENCE and ATTRIBUTE must be a tag, written e.g.
-   *  "(0010,0010)" or as a dictionary name, e.g. "PatientName".
-   *
-   *  Example: The path
-   *  "ContentSequence[4].(0040,a043)[0].CodeValue" selects the Content
-   *  Sequence in the given object, therein the 5th item, therein the "Concept
-   *  Name Code Sequence" denoted by (0040,a043), therein the first item
-   *  and finally therein the tag "Code Value". Only "Code Value" will be
-   *  deleted by the function.
-   *  @param obj [in] The object to delete attribute or item from
-   *  @param path [in] The path either starting with an attribute (either a
-   *              sequence or a leaf attribute as a dictionary name or tag) or
-   *              starting with an item
-   *  @param numDeleted [out] Number of deleted attributes/items
-   *  @return EC_Normal if successful, error code otherwise. If the desired
-   *  attribute/item was not found, EC_TagNotFound is returned.
-   */
-  OFCondition findOrDeletePath(DcmObject* obj,
-                               const OFString& path,
-                               Uint32& numDeleted);
-
-  /** Returns the results from the search / creation call.
-   *  @param searchResults [out] The resulting paths that were created/searched
-   *                       Note that the memory of the search results is freed
-   *                       automatically by the destructor and must not be freed
-   *                       by the caller.
-   *  @return Number of results returned
-   */
-  Uint32 getResults(OFList<DcmPath*>& searchResults);
-
-
-  /** Helper function that applies a specified "override key" in path syntax
-   *  to the given dataset. The name "override" indicates that these keys have
-   *  higher precedence than identical keys in a request dataset that might
-   *  possibly read from a DICOM query file.
-   *  @param dataset [in/out] the dataset (e.g.\ query keys) the override key is
-   *                 applied to. Must be non-NULL.
-   *  @param overrideKey [in] the override key in path syntax (see class DcmPath).
-   *                     Also the path can end with a value assignment, e.g.
-   *                     "PatientName=Doe^John". An empty (or missing value) will
-   *                     not be ignored but will be written as empty to the
-   *                     attribute (if not a sequence or item).
-   *  @return EC_Normal if adding was successful, error code otherwise
-   */
-  OFCondition applyPathWithValue(DcmDataset* dataset,
-                                 const OFString& overrideKey);
-
-  /** Destructor, cleans up memory that was allocated for any search results.
-   */
-  ~DcmPathProcessor();
+    /** Constructor, creates an empty search object.
+     */
+    DcmPathProcessor();
+
+    /** Sets whether searching/creating paths will support wildcard for
+     *  items. If set to false, any path operation with item wildcard characters
+     *  will return an error.
+     *  @param supported [in] If true, wildcard are enabled (default)
+     *                   If false, item wildcard support is disabled.
+     */
+    void setItemWildcardSupport(const OFBool supported);
+
+    /** Enables (class default: enabled) or disables checking of private
+     *  reservations when inserting private tags. If enabled and a private
+     *  tag is created that has no private reservation, an error is returned.
+     *  If disabled, it is possible to insert private tags that do not have
+     *  a reservation in the corresponding item/dataset.
+     *  @param doChecking [in] OFTrue enables reservation checking,
+     *                    OFFalse disables it.
+     */
+    void checkPrivateReservations(const OFBool doChecking);
+
+    /** Returns private creator string for given tag
+     *  @param item   [in] The item to search in
+     *  @param tagKey [in] The tag key for which a reservation should be looked up
+     *  @param privateCreator [out] The private creator string
+     *  @return Return EC_Normal if reservation was found (can be empty, though),
+     *          EC_TagNotFound if no private creator tag exists, error otherwise
+     */
+    static OFCondition getPrivateCreator(DcmItem* item, const DcmTagKey& tagKey, OFString& privateCreator);
+
+    /** Checks in item, whether a private reservation for a given
+     *  tag key exists.
+     *  @param item   [in] The item to search in
+     *  @param tagKey [in/out] The tag to be checked.
+     *  @param privateCreator [in] The private creator to check for (if known,
+     *                        can be left empty)
+     *  @return Return EC_Normal if reservation checking was successful.
+     *          Otherwise an error code is returned.
+     */
+    static OFCondition
+    checkPrivateTagReservation(DcmItem* item, const DcmTagKey& tagKey, const OFString& privateCreator = "");
+
+    /** Checks in item, whether a private reservation for a given
+     *  tag key. If so, a dictionary lookup is performed and the VR and private
+     *  creator of the tag is updated correspondingly.
+     *  @param item [in] The item to search in
+     *  @param tag [in/out] The tag to be checked. Will be updated with VR and
+     *                      private creator.
+     *  @param privateCreator [in] The private creator to check for (if known,
+     *                        can be left empty)
+     *  @return Return EC_Normal if reservation checking and updating the
+     *          tag was successful. Otherwise an error code is returned.
+     */
+    static OFCondition checkPrivateTagReservation(DcmItem* item, DcmTag& tag, const OFString& privateCreator = "");
+
+    /** Function that allows for finding and/or inserting a hierarchy of items
+     *  and attributes as defined by a path string; also returns a list of
+     *  pointers for each successfully found or inserted paths. Every list
+     *  contains pointers pointing to all the objects along the path
+     *  starting from the object given as parameter. The pointer to the
+     *  starting object will not be part of the result.
+     *
+     *  In principle, the path string must have the following format (in
+     *  arbitrary depth). Note that for searching a sequence, the example
+     *  below would start with [ITEMNO] instead:
+     *  SEQUENCE[ITEMNO].SEQUENCE[ITEMNO].ATTRIBUTE
+     *  . ITEMNO must be a positive integer starting with 0.
+     *  SEQUENCE and ATTRIBUTE must be a tag, written e.g.
+     *  "(0010,0010)" or as a dictionary name, e.g. "PatientName". If the
+     *  path cannot be fully created (see option createIfNecessary), any
+     *  possibly object changes are reverted. So a path is either fully created
+     *  or no path component is created at all. The result can be obtained
+     *  by calling the getResults() function.
+     *
+     *  Example: The path
+     *  "ContentSequence[4].(0040,a043)[0].CodeValue" selects the Content
+     *  Sequence in the given object, therein the 5th item, therein the "Concept
+     *  Name Code Sequence" denoted by (0040,a043), therein the first item
+     *  and finally therein the tag "Code Value".
+     *  The resulting object list should (if success is returned) contain
+     *  1 result, consisting of a list with 5 pointers to 5 objects in the order
+     *  in their logical order as they occur in the path string
+     *  (in total 2 sequences, 2 items, and one leaf attribute).
+     *  @param obj [in] The object to search (or create) a path in
+     *  @param path [in] The path either starting with an attribute (either a
+     *              sequence or a leaf attribute as a dictionary name or tag) or
+     *              starting with an item
+     *  @param createIfNecessary [in] If set, all missing objects found
+     *                           in the path string are created. If not set,
+     *                           only existing paths can be accessed and
+     *                           no new attribute or item is created.
+     *  @return EC_Normal if successful, error code otherwise.
+     */
+    OFCondition findOrCreatePath(DcmObject* obj, const OFString& path, OFBool createIfNecessary = OFFalse);
+
+    /** Function that allows for deleting elements and items from
+     *  a DICOM object tree.
+     *  In principle, the path string must have the following format (in
+     *  arbitrary depth). Note that for searching in a sequence, the example
+     *  below would start with [ITEMNO] instead:
+     *  SEQUENCE[ITEMNO].SEQUENCE[ITEMNO].ATTRIBUTE
+     *  . ITEMNO must be a positive integer starting with 0.
+     *  SEQUENCE and ATTRIBUTE must be a tag, written e.g.
+     *  "(0010,0010)" or as a dictionary name, e.g. "PatientName".
+     *
+     *  Example: The path
+     *  "ContentSequence[4].(0040,a043)[0].CodeValue" selects the Content
+     *  Sequence in the given object, therein the 5th item, therein the "Concept
+     *  Name Code Sequence" denoted by (0040,a043), therein the first item
+     *  and finally therein the tag "Code Value". Only "Code Value" will be
+     *  deleted by the function.
+     *  @param obj [in] The object to delete attribute or item from
+     *  @param path [in] The path either starting with an attribute (either a
+     *              sequence or a leaf attribute as a dictionary name or tag) or
+     *              starting with an item
+     *  @param numDeleted [out] Number of deleted attributes/items
+     *  @return EC_Normal if successful, error code otherwise. If the desired
+     *  attribute/item was not found, EC_TagNotFound is returned.
+     */
+    OFCondition findOrDeletePath(DcmObject* obj, const OFString& path, Uint32& numDeleted);
+
+    /** Returns the results from the search / creation call.
+     *  @param searchResults [out] The resulting paths that were created/searched
+     *                       Note that the memory of the search results is freed
+     *                       automatically by the destructor and must not be freed
+     *                       by the caller.
+     *  @return Number of results returned
+     */
+    Uint32 getResults(OFList<DcmPath*>& searchResults);
+
+    /** Helper function that applies a specified "override key" in path syntax
+     *  to the given dataset. The name "override" indicates that these keys have
+     *  higher precedence than identical keys in a request dataset that might
+     *  possibly read from a DICOM query file.
+     *  @param dataset [in/out] the dataset (e.g.\ query keys) the override key is
+     *                 applied to. Must be non-NULL.
+     *  @param overrideKey [in] the override key in path syntax (see class DcmPath).
+     *                     Also the path can end with a value assignment, e.g.
+     *                     "PatientName=Doe^John". An empty (or missing value) will
+     *                     not be ignored but will be written as empty to the
+     *                     attribute (if not a sequence or item).
+     *  @return EC_Normal if adding was successful, error code otherwise
+     */
+    OFCondition applyPathWithValue(DcmDataset* dataset, const OFString& overrideKey);
+
+    /** Destructor, cleans up memory that was allocated for any search results.
+     */
+    ~DcmPathProcessor();
 
 protected:
-
-  /** Function that allows for finding and/or inserting a hierarchy of items
-   *  and attributes as defined by a path string; also returns a list of
-   *  pointers for each successfully found or inserted paths. Every list
-   *  contains pointers pointing to all the objects along the path
-   *  starting from the object given as parameter. The pointer to the
-   *  starting object will not be part of the result.
-   *
-   *  In principle, the path string must have the following format (in
-   *  arbitrary depth).
-   *  SEQUENCE[ITEMNO].SEQUENCE[ITEMNO].ATTRIBUTE
-   *  . ITEMNO must be a positive integer starting with 0.
-   *  SEQUENCE and ATTRIBUTE must be a tag, written e.g.
-   *  "(0010,0010)" or as a dictionary name, e.g. "PatientName". If the
-   *  path cannot be fully created (see option createIfNecessary), any
-   *  possibly object changes are reverted. So a path is either fully created
-   *  or no path component is created at all. The result can be obtained
-   *  by calling the getResults() function.
-   *
-   *  Example: The path
-   *  "ContentSequence[4].(0040,a043)[0].CodeValue" selects the Content
-   *  Sequence in the given item, therein the 5th item, therein the "Concept
-   *  Name Code Sequence" denoted by (0040,a043), therein the first item
-   *  and finally therein the tag "Code Value".
-   *  The resulting object list should (if success is returned) contain
-   *  1 result, consisting of a list with 5 pointers to 5 objects in the order
-   *  in their logical order as they occur in the path string
-   *  (in total 2 sequences, 2 items, and one leaf attribute).
-   *  @param item [in] The object to search (or create) a path in
-   *  @param path [in] The path starting with an attribute (either a
-   *              sequence or a leaf attribute) as a dictionary name or tag.
-   *              The parsed attribute is removed from the path string.
-   *  @return EC_Normal if successful, error code otherwise.
-   */
-  OFCondition findOrCreateItemPath(DcmItem* item,
-                                   OFString& path);
-
-  /** Function that allows for finding and/or inserting a hierarchy of items
-   *  and attributes as defined by a path string; also returns a list of
-   *  pointers for each successfully found or inserted paths. Every list
-   *  contains pointers pointing to all the objects along the path
-   *  starting from the object given as parameter. The pointer to the
-   *  starting object will not be part of the result.
-   *
-   *  In principle, the path string must have the following format (in
-   *  arbitrary depth).
-   *  [ITEMNO].SEQUENCE[ITEMNO].ATTRIBUTE
-   *  . ITEMNO must be a positive integer starting with 0.
-   *  SEQUENCE and ATTRIBUTE must be a tag, written e.g.
-   *  "(0010,0010)" or as a dictionary name, e.g. "PatientName". If the
-   *  path cannot be fully created (see option createIfNecessary), any
-   *  possibly object changes are reverted. So a path is either fully created
-   *  or no path component is created at all. The result can be obtained
-   *  by calling the getResults() function.
-   *
-   *  Example: The path
-   *  "[4].(0040,a043)[0].CodeValue" selects the 5th item in the given
-   *  sequence, therein the "Concept Name Code Sequence" denoted by
-   *  (0040,a043), therein the first item and finally therein the
-   *  tag "Code Value".
-   *  The resulting object list should (if success is returned) contain
-   *  1 result, consisting of a list with 4 pointers to 4 objects in the order
-   *  in their logical order as they occur in the path string
-   *  (in total 1 sequence, 2 items, and one leaf element).
-   *  @param seq  [in] The object to search (or create) a path in
-   *  @param path [in] The path starting with an item. The parsed item number
-   *  (e.g. "[0]") is removed from the path string.
-   *  @return EC_Normal if successful, error code otherwise.
-   */
-  OFCondition findOrCreateSequencePath(DcmSequenceOfItems* seq,
-                                       OFString& path);
-
-  /** Helper function that looks at the last node in a given path and deletes
-   *  the corresponding DICOM object. Does not delete the path node itself:
-   *  That is done by the calling function, findOrCreateItemPath().
-   *  @param objSearchedIn [in/out] The object the given path starts in.
-   *  @param path [in/out] The complete path to the DICOM object to delete
-   *  @param toDelete [in/out] The path node to delete. This node must be
-   *                  identical to the last node in the path parameter. Also
-   *                  the node must represent a DICOM sequence or leaf element,
-   *                  not an item. However, because it is isolated already by
-   *                  the calling function, it is provided here for convenience.
-   */
-  static OFCondition deleteLastElemFromPath(DcmObject* objSearchedIn,
-                                            DcmPath* path,
-                                            DcmPathNode* toDelete);
-
-  /** Helper function that looks at the last node in a given path and deletes
-   *  the corresponding DICOM object. Does not delete the path node itself:
-   *  That is done by the calling function, findOrCreateItemPath().
-   *  @param objSearchedIn [in/out] The object the given path starts in.
-   *  @param path [in/out] The complete path to the DICOM object to delete
-   *  @param toDelete [in/out] The path node to delete. This node must be
-   *                  identical to the last node in the path parameter. Also
-   *                  the node must represent a DICOM item, not a sequence
-   *                  However, because it is isolated already by the calling
-   *                  function, it is provided here for convenience.
-   */
-  static OFCondition deleteLastItemFromPath(DcmObject* objSearchedIn,
-                                            DcmPath* path,
-                                            DcmPathNode* toDelete);
-
-  /** Returns the private reservation tag key for a given private tag
-   *  @param privateKey [in] The private key to calculate reservation tag for
-   *  @return The reservation key. If given key is not private or an error,
-   *          return DCM_UndefinedTagKey. If the given key is a reservation
-   *          itself, it is directly returned.
-   */
-  static DcmTagKey calcPrivateReservationTag(const DcmTagKey& privateKey);
-
-  /** Cleans up memory that was allocated for any search results.
-   *  Called when a new search is started or during object destruction.
-   *  The DICOM data all freed paths and path nodes point to, is not
-   *  touched, i.e. all memory to the DICOM objects pointed to must be
-   *  freed from outside. Processing options like checking for private
-   *  reservations and so on are not reset to default values but
-   *  keep valid.
-   */
-  void clear();
+    /** Function that allows for finding and/or inserting a hierarchy of items
+     *  and attributes as defined by a path string; also returns a list of
+     *  pointers for each successfully found or inserted paths. Every list
+     *  contains pointers pointing to all the objects along the path
+     *  starting from the object given as parameter. The pointer to the
+     *  starting object will not be part of the result.
+     *
+     *  In principle, the path string must have the following format (in
+     *  arbitrary depth).
+     *  SEQUENCE[ITEMNO].SEQUENCE[ITEMNO].ATTRIBUTE
+     *  . ITEMNO must be a positive integer starting with 0.
+     *  SEQUENCE and ATTRIBUTE must be a tag, written e.g.
+     *  "(0010,0010)" or as a dictionary name, e.g. "PatientName". If the
+     *  path cannot be fully created (see option createIfNecessary), any
+     *  possibly object changes are reverted. So a path is either fully created
+     *  or no path component is created at all. The result can be obtained
+     *  by calling the getResults() function.
+     *
+     *  Example: The path
+     *  "ContentSequence[4].(0040,a043)[0].CodeValue" selects the Content
+     *  Sequence in the given item, therein the 5th item, therein the "Concept
+     *  Name Code Sequence" denoted by (0040,a043), therein the first item
+     *  and finally therein the tag "Code Value".
+     *  The resulting object list should (if success is returned) contain
+     *  1 result, consisting of a list with 5 pointers to 5 objects in the order
+     *  in their logical order as they occur in the path string
+     *  (in total 2 sequences, 2 items, and one leaf attribute).
+     *  @param item [in] The object to search (or create) a path in
+     *  @param path [in] The path starting with an attribute (either a
+     *              sequence or a leaf attribute) as a dictionary name or tag.
+     *              The parsed attribute is removed from the path string.
+     *  @return EC_Normal if successful, error code otherwise.
+     */
+    OFCondition findOrCreateItemPath(DcmItem* item, OFString& path);
+
+    /** Function that allows for finding and/or inserting a hierarchy of items
+     *  and attributes as defined by a path string; also returns a list of
+     *  pointers for each successfully found or inserted paths. Every list
+     *  contains pointers pointing to all the objects along the path
+     *  starting from the object given as parameter. The pointer to the
+     *  starting object will not be part of the result.
+     *
+     *  In principle, the path string must have the following format (in
+     *  arbitrary depth).
+     *  [ITEMNO].SEQUENCE[ITEMNO].ATTRIBUTE
+     *  . ITEMNO must be a positive integer starting with 0.
+     *  SEQUENCE and ATTRIBUTE must be a tag, written e.g.
+     *  "(0010,0010)" or as a dictionary name, e.g. "PatientName". If the
+     *  path cannot be fully created (see option createIfNecessary), any
+     *  possibly object changes are reverted. So a path is either fully created
+     *  or no path component is created at all. The result can be obtained
+     *  by calling the getResults() function.
+     *
+     *  Example: The path
+     *  "[4].(0040,a043)[0].CodeValue" selects the 5th item in the given
+     *  sequence, therein the "Concept Name Code Sequence" denoted by
+     *  (0040,a043), therein the first item and finally therein the
+     *  tag "Code Value".
+     *  The resulting object list should (if success is returned) contain
+     *  1 result, consisting of a list with 4 pointers to 4 objects in the order
+     *  in their logical order as they occur in the path string
+     *  (in total 1 sequence, 2 items, and one leaf element).
+     *  @param seq  [in] The object to search (or create) a path in
+     *  @param path [in] The path starting with an item. The parsed item number
+     *  (e.g. "[0]") is removed from the path string.
+     *  @return EC_Normal if successful, error code otherwise.
+     */
+    OFCondition findOrCreateSequencePath(DcmSequenceOfItems* seq, OFString& path);
+
+    /** Helper function that looks at the last node in a given path and deletes
+     *  the corresponding DICOM object. Does not delete the path node itself:
+     *  That is done by the calling function, findOrCreateItemPath().
+     *  @param objSearchedIn [in/out] The object the given path starts in.
+     *  @param path [in/out] The complete path to the DICOM object to delete
+     *  @param toDelete [in/out] The path node to delete. This node must be
+     *                  identical to the last node in the path parameter. Also
+     *                  the node must represent a DICOM sequence or leaf element,
+     *                  not an item. However, because it is isolated already by
+     *                  the calling function, it is provided here for convenience.
+     *  @return EC_Normal if successful, error otherwise
+     */
+    static OFCondition deleteLastElemFromPath(DcmObject* objSearchedIn, DcmPath* path, DcmPathNode* toDelete);
+
+    /** Helper function that looks at the last node in a given path and deletes
+     *  the corresponding DICOM object. Does not delete the path node itself:
+     *  That is done by the calling function, findOrCreateItemPath().
+     *  @param objSearchedIn [in/out] The object the given path starts in.
+     *  @param path [in/out] The complete path to the DICOM object to delete
+     *  @param toDelete [in/out] The path node to delete. This node must be
+     *                  identical to the last node in the path parameter. Also
+     *                  the node must represent a DICOM item, not a sequence
+     *                  However, because it is isolated already by the calling
+     *                  function, it is provided here for convenience.
+     *  @return EC_Normal if successful, error otherwise
+     */
+    static OFCondition deleteLastItemFromPath(DcmObject* objSearchedIn, DcmPath* path, DcmPathNode* toDelete);
+
+    /** Returns the private reservation tag key for a given private tag
+     *  @param privateKey [in] The private key to calculate reservation tag for
+     *  @return The reservation key. If given key is not private or an error,
+     *          return DCM_UndefinedTagKey. If the given key is a reservation
+     *          itself, it is directly returned.
+     */
+    static DcmTagKey calcPrivateReservationTag(const DcmTagKey& privateKey);
+
+    /** Cleans up memory that was allocated for any search results.
+     *  Called when a new search is started or during object destruction.
+     *  The DICOM data all freed paths and path nodes point to, is not
+     *  touched, i.e. all memory to the DICOM objects pointed to must be
+     *  freed from outside. Processing options like checking for private
+     *  reservations and so on are not reset to default values but
+     *  keep valid.
+     */
+    void clear();
 
 private:
-
-  /// Internal list that is during search for keeping track of current path
-  OFList<DcmPathNode*> m_currentPath;
-
-  /// Internal list that represents the search results found
-  OFList<DcmPath*> m_results;
-
-  /// Denotes whether missing items/sequences/attributes should be
-  /// automatically inserted when using findAndCreate routines
-  OFBool m_createIfNecessary;
-
-  /// If enabled (default), any insertions of private tags will fail, if no
-  /// corresponding reservation exists in the underlying item
-  OFBool m_checkPrivateReservations;
-
-  /// Denotes, whether a path is accepted that contains wildcards.
-  /// If false, then any search containing wildcards will return an error.
-  OFBool m_itemWildcardsEnabled;
-
-  /** Private undefined copy constructor
-   */
-  DcmPathProcessor(const DcmPathProcessor& rhs);
-
-  /** Private undefined assignment operator
-   */
-  DcmPathProcessor& operator=(const DcmPathProcessor& arg);
+    /// Internal list that is during search for keeping track of current path
+    OFList<DcmPathNode*> m_currentPath;
+
+    /// Internal list that represents the search results found
+    OFList<DcmPath*> m_results;
+
+    /// Denotes whether missing items/sequences/attributes should be
+    /// automatically inserted when using findAndCreate routines
+    OFBool m_createIfNecessary;
+
+    /// If enabled (default), any insertions of private tags will fail, if no
+    /// corresponding reservation exists in the underlying item
+    OFBool m_checkPrivateReservations;
+
+    /// Denotes, whether a path is accepted that contains wildcards.
+    /// If false, then any search containing wildcards will return an error.
+    OFBool m_itemWildcardsEnabled;
+
+    /** Private undefined copy constructor
+     *  @param rhs Object to copy from
+     */
+    DcmPathProcessor(const DcmPathProcessor& rhs);
+
+    /** Private undefined assignment operator
+     *  @param arg Object to copy from
+     *  @return Reference to this object
+     */
+    DcmPathProcessor& operator=(const DcmPathProcessor& arg);
 };
 
-
 #endif // DCPATH_H
index 3235f9d2322aa354bc4b6704ef1f5d3cfdbb8723..c6dccc02bea871dc0a1fcf677889682911bb78a6 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -341,10 +341,7 @@ public:
     virtual OFBool canWriteXfer(const E_TransferSyntax newXfer,
                                 const E_TransferSyntax oldXfer);
 
-    /** returns length of representation conforming to the
-     *  transfer syntax with tag, vr, ... It does not create a
-     *  representation. If no conforming representation exists an
-     *  error code is set and 0 returned.
+    /** @copydoc DcmObject::calcElementLength()
      */
     virtual Uint32 calcElementLength(const E_TransferSyntax xfer,
                                      const E_EncodingType enctype);
@@ -400,6 +397,14 @@ public:
     virtual OFCondition writeXML(STD_NAMESPACE ostream &out,
                                  const size_t flags = 0);
 
+    /** write object in JSON format to a stream
+     *  @param out output stream to which the JSON document is written
+     *  @param format used to format and customize the output
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition writeJson(STD_NAMESPACE ostream &out,
+                                  DcmJsonFormat &format);
+
     /** special write method for creation of digital signatures
      *  @param outStream DICOM output stream
      *  @param oxfer output transfer syntax
index 435c7bfb48e11f25e30e50327451bcd4846fd8d5..77155b3238094fe81c1249b7e1679a8b55fed45f 100644 (file)
@@ -47,6 +47,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition decode(
@@ -54,7 +58,8 @@ public:
     DcmPixelSequence * pixSeq,
     DcmPolymorphOBOW& uncompressedPixelData,
     const DcmCodecParameter * cp,
-    const DcmStack& objStack) const;
+    const DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** decompresses a single frame from the given pixel sequence and
    *  stores the result in the given buffer.
@@ -104,6 +109,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition encode(
@@ -112,7 +121,8 @@ public:
     const DcmRepresentationParameter * toRepParam,
     DcmPixelSequence * & pixSeq,
     const DcmCodecParameter *cp,
-    DcmStack & objStack) const;
+    DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** transcodes (re-compresses) the given compressed DICOM image and stores
    *  the result in the given toPixSeq element.
@@ -126,6 +136,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition encode(
@@ -135,7 +149,8 @@ public:
     const DcmRepresentationParameter * toRepParam,
     DcmPixelSequence * & toPixSeq,
     const DcmCodecParameter * cp,
-    DcmStack & objStack) const;
+    DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** checks if this codec is able to convert from the
    *  given current transfer syntax to the given new
index 2b983240128244094efeb8e025ed6855ff0fd070..4e36cea1e3de933859e096653e674e3ddcca9e4e 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2002-2011, OFFIS e.V.
+ *  Copyright (C) 2002-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -49,6 +49,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition decode(
@@ -56,7 +60,8 @@ public:
     DcmPixelSequence * pixSeq,
     DcmPolymorphOBOW& uncompressedPixelData,
     const DcmCodecParameter * cp,
-    const DcmStack& objStack) const;
+    const DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** decompresses a single frame from the given pixel sequence and
    *  stores the result in the given buffer.
@@ -106,6 +111,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition encode(
@@ -114,7 +123,8 @@ public:
     const DcmRepresentationParameter * toRepParam,
     DcmPixelSequence * & pixSeq,
     const DcmCodecParameter *cp,
-    DcmStack & objStack) const;
+    DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** transcodes (re-compresses) the given compressed DICOM image and stores
    *  the result in the given toPixSeq element.
@@ -128,6 +138,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition encode(
@@ -137,7 +151,8 @@ public:
     const DcmRepresentationParameter * toRepParam,
     DcmPixelSequence * & toPixSeq,
     const DcmCodecParameter * cp,
-    DcmStack & objStack) const;
+    DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** checks if this codec is able to convert from the
    *  given current transfer syntax to the given new
index 62efe13075768d5a1d0c283e389f9da8abe84798..36a490b089ad89e0960203b05c503d296d4c1d8d 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -207,21 +207,7 @@ public:
                              const Uint32 subPadlen = 0,
                              Uint32 instanceLength = 0);
 
-    /** calculate the length of this DICOM element when encoded with the
-     *  given transfer syntax and the given encoding type for sequences.
-     *  For elements, the length includes the length of the tag, length field,
-     *  VR field and the value itself, for items and sequences it returns
-     *  the length of the complete item or sequence including delimitation tags
-     *  if applicable.
-     *  If length encoding is set to be explicit and the total sequence size is
-     *  larger than the available 32-bit length field, then undefined length
-     *  is returned. If "dcmWriteOversizedSeqsAndItemsUndefined" is disabled,
-     *  also the internal DcmObject errorFlag is set to EC_SeqOrItemContentOverflow
-     *  in case the sequence content (excluding tag header etc.) is already too
-     *  large.
-     *  @param xfer transfer syntax for length calculation
-     *  @param enctype sequence encoding type for length calculation
-     *  @return length of DICOM element
+    /** @copydoc DcmObject::calcElementLength()
      */
     virtual Uint32 calcElementLength(const E_TransferSyntax xfer,
                                      const E_EncodingType enctype);
index 7a6fafe56a2cb002cb9db63798d5eaad8d035685..16207a4af4b417aa2945ccd9a6add835ac0484a5 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -369,6 +369,12 @@ DCMTK_DCMDATA_EXPORT unsigned long dcmGuessModalityBytes(const char *sopClassUID
 #define UID_HEVCMain10ProfileLevel5_1TransferSyntax "1.2.840.10008.1.2.4.108"
 /// RLE Lossless
 #define UID_RLELosslessTransferSyntax           "1.2.840.10008.1.2.5"
+/// SMPTE ST 2110-20 Uncompressed Progressive Active Video
+#define UID_SMPTEST2110_20_UncompressedProgressiveActiveVideoTransferSyntax "1.2.840.10008.1.2.7.1"
+/// SMPTE ST 2110-20 Uncompressed Interlaced Active Video
+#define UID_SMPTEST2110_20_UncompressedInterlacedActiveVideoTransferSyntax "1.2.840.10008.1.2.7.2"
+/// SMPTE ST 2110-30 PCM Digital Audio
+#define UID_SMPTEST2110_30_PCMDigitalAudioTransferSyntax "1.2.840.10008.1.2.7.3"
 
 /** RFC 2557 MIME Encapsulation (RETIRED) was only a pseudo transfer syntax used
  *  to refer to MIME encapsulated HL7 CDA documents from a DICOMDIR when stored
@@ -433,6 +439,12 @@ DCMTK_DCMDATA_EXPORT unsigned long dcmGuessModalityBytes(const char *sopClassUID
 #define UID_GeneralAudioWaveformStorage                            "1.2.840.10008.5.1.4.1.1.9.4.2"
 #define UID_ArterialPulseWaveformStorage                           "1.2.840.10008.5.1.4.1.1.9.5.1"
 #define UID_RespiratoryWaveformStorage                             "1.2.840.10008.5.1.4.1.1.9.6.1"
+#define UID_MultichannelRespiratoryWaveformStorage                 "1.2.840.10008.5.1.4.1.1.9.6.2"
+#define UID_RoutineScalpElectroencephalogramWaveformStorage        "1.2.840.10008.5.1.4.1.1.9.7.1"
+#define UID_ElectromyogramWaveformStorage                          "1.2.840.10008.5.1.4.1.1.9.7.2"
+#define UID_ElectrooculogramWaveformStorage                        "1.2.840.10008.5.1.4.1.1.9.7.3"
+#define UID_SleepElectroencephalogramWaveformStorage               "1.2.840.10008.5.1.4.1.1.9.7.4"
+#define UID_BodyPositionWaveformStorage                            "1.2.840.10008.5.1.4.1.1.9.8.1"
 #define UID_RETIRED_StandaloneModalityLUTStorage                   "1.2.840.10008.5.1.4.1.1.10"
 #define UID_RETIRED_StandaloneVOILUTStorage                        "1.2.840.10008.5.1.4.1.1.11"
 #define UID_GrayscaleSoftcopyPresentationStateStorage              "1.2.840.10008.5.1.4.1.1.11.1"
@@ -487,6 +499,7 @@ DCMTK_DCMDATA_EXPORT unsigned long dcmGuessModalityBytes(const char *sopClassUID
 #define UID_OphthalmicOpticalCoherenceTomographyEnFaceImageStorage "1.2.840.10008.5.1.4.1.1.77.1.5.7"
 #define UID_OphthalmicOpticalCoherenceTomographyBscanVolumeAnalysisStorage "1.2.840.10008.5.1.4.1.1.77.1.5.8"
 #define UID_VLWholeSlideMicroscopyImageStorage                     "1.2.840.10008.5.1.4.1.1.77.1.6"
+#define UID_DermoscopicPhotographyImageStorage                     "1.2.840.10008.5.1.4.1.1.77.1.7"
 #define UID_RETIRED_VLMultiframeImageStorage                       "1.2.840.10008.5.1.4.1.1.77.2"
 #define UID_LensometryMeasurementsStorage                          "1.2.840.10008.5.1.4.1.1.78.1"
 #define UID_AutorefractionMeasurementsStorage                      "1.2.840.10008.5.1.4.1.1.78.2"
@@ -522,6 +535,8 @@ DCMTK_DCMDATA_EXPORT unsigned long dcmGuessModalityBytes(const char *sopClassUID
 #define UID_EncapsulatedPDFStorage                                 "1.2.840.10008.5.1.4.1.1.104.1"
 #define UID_EncapsulatedCDAStorage                                 "1.2.840.10008.5.1.4.1.1.104.2"
 #define UID_EncapsulatedSTLStorage                                 "1.2.840.10008.5.1.4.1.1.104.3"
+#define UID_EncapsulatedOBJStorage                                 "1.2.840.10008.5.1.4.1.1.104.4"
+#define UID_EncapsulatedMTLStorage                                 "1.2.840.10008.5.1.4.1.1.104.5"
 #define UID_PositronEmissionTomographyImageStorage                 "1.2.840.10008.5.1.4.1.1.128"
 #define UID_LegacyConvertedEnhancedPETImageStorage                 "1.2.840.10008.5.1.4.1.1.128.1"
 #define UID_RETIRED_StandalonePETCurveStorage                      "1.2.840.10008.5.1.4.1.1.129"
@@ -543,6 +558,13 @@ DCMTK_DCMDATA_EXPORT unsigned long dcmGuessModalityBytes(const char *sopClassUID
 #define UID_RTSegmentAnnotationStorage                             "1.2.840.10008.5.1.4.1.1.481.11"
 #define UID_RTRadiationSetStorage                                  "1.2.840.10008.5.1.4.1.1.481.12"
 #define UID_CArmPhotonElectronRadiationStorage                     "1.2.840.10008.5.1.4.1.1.481.13"
+#define UID_TomotherapeuticRadiationStorage                        "1.2.840.10008.5.1.4.1.1.481.14"
+#define UID_RoboticArmRadiationStorage                             "1.2.840.10008.5.1.4.1.1.481.15"
+#define UID_RTRadiationRecordSetStorage                            "1.2.840.10008.5.1.4.1.1.481.16"
+#define UID_RTRadiationSalvageRecordStorage                        "1.2.840.10008.5.1.4.1.1.481.17"
+#define UID_TomotherapeuticRadiationRecordStorage                  "1.2.840.10008.5.1.4.1.1.481.18"
+#define UID_CArmPhotonElectronRadiationRecordStorage               "1.2.840.10008.5.1.4.1.1.481.19"
+#define UID_RoboticRadiationRecordStorage                          "1.2.840.10008.5.1.4.1.1.481.20"
 #define UID_RTBeamsDeliveryInstructionStorage                      "1.2.840.10008.5.1.4.34.7"
 #define UID_RTBrachyApplicationSetupDeliveryInstructionStorage     "1.2.840.10008.5.1.4.34.10"
 #define UID_HangingProtocolStorage                                 "1.2.840.10008.5.1.4.38.1"
@@ -604,6 +626,7 @@ DCMTK_DCMDATA_EXPORT unsigned long dcmGuessModalityBytes(const char *sopClassUID
 #define UID_UnifiedProcedureStepWatchSOPClass                      "1.2.840.10008.5.1.4.34.6.2"
 #define UID_UnifiedProcedureStepPullSOPClass                       "1.2.840.10008.5.1.4.34.6.3"
 #define UID_UnifiedProcedureStepEventSOPClass                      "1.2.840.10008.5.1.4.34.6.4"
+#define UID_UnifiedProcedureStepQuerySOPClass                      "1.2.840.10008.5.1.4.34.6.5"
 #define UID_UPSGlobalSubscriptionSOPInstance                       "1.2.840.10008.5.1.4.34.5"
 #define UID_UPSFilteredGlobalSubscriptionSOPInstance               "1.2.840.10008.5.1.4.34.5.1"
 
@@ -618,6 +641,7 @@ DCMTK_DCMDATA_EXPORT unsigned long dcmGuessModalityBytes(const char *sopClassUID
 #define UID_MOVEHangingProtocolInformationModel                    "1.2.840.10008.5.1.4.38.3"
 
 // Relevant Patient Information Query
+#define UID_RelevantPatientInformationQuery_Prefix                 "1.2.840.10008.5.1.4.37."
 #define UID_GeneralRelevantPatientInformationQuery                 "1.2.840.10008.5.1.4.37.1"
 #define UID_BreastImagingRelevantPatientInformationQuery           "1.2.840.10008.5.1.4.37.2"
 #define UID_CardiacRelevantPatientInformationQuery                 "1.2.840.10008.5.1.4.37.3"
@@ -711,6 +735,12 @@ DCMTK_DCMDATA_EXPORT unsigned long dcmGuessModalityBytes(const char *sopClassUID
 #define UID_DisplaySystemSOPClass                                  "1.2.840.10008.5.1.1.40"
 #define UID_DisplaySystemSOPInstance                               "1.2.840.10008.5.1.1.40.1"
 
+// Real-Time Video
+#define UID_VideoEndoscopicImageRealTimeCommunication              "1.2.840.10008.10.1"
+#define UID_VideoPhotographicImageRealTimeCommunication            "1.2.840.10008.10.2"
+#define UID_AudioWaveformRealTimeCommunication                     "1.2.840.10008.10.3"
+#define UID_RenditionSelectionDocumentRealTimeCommunication        "1.2.840.10008.10.4"
+
 // Other
 #define UID_VerificationSOPClass                                   "1.2.840.10008.1.1"
 #define UID_RETIRED_BasicStudyContentNotificationSOPClass          "1.2.840.10008.1.9"
@@ -793,6 +823,12 @@ DCMTK_DCMDATA_EXPORT unsigned long dcmGuessModalityBytes(const char *sopClassUID
 #define UID_ICBM452T1FrameOfReference                              "1.2.840.10008.1.4.2.1"
 #define UID_ICBMSingleSubjectMRIFrameOfReference                   "1.2.840.10008.1.4.2.2"
 #define UID_IEC61217FixedCoordinateSystemFrameOfReference          "1.2.840.10008.1.4.3.1"
+#define UID_StandardRoboticCoordinateSystemFrameOfReference        "1.2.840.10008.1.4.3.2"
+#define UID_SRI24FrameOfReference                                  "1.2.840.10008.1.4.4.1"
+#define UID_Colin27FrameOfReference                                "1.2.840.10008.1.4.5.1"
+#define UID_LPBA40AIRFrameOfReference                              "1.2.840.10008.1.4.6.1"
+#define UID_LPBA40FLIRTFrameOfReference                            "1.2.840.10008.1.4.6.2"
+#define UID_LPBA40SPM5FrameOfReference                             "1.2.840.10008.1.4.6.3"
 
 // Well-known SOP Instances for Color Palettes
 #define UID_HotIronColorPaletteSOPInstance                         "1.2.840.10008.1.5.1"
index a643392b40f4b1eeb730cf7ff366f64d1ae69671..f7584a75f7f8f378a0d4824653846f6a0e663e94 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -221,6 +221,9 @@ enum DcmEVR
     /// OB or OW depending on context
     EVR_ox,
 
+    /// OB or OW, interpreted as pixel data (compressed or uncompressed)
+    EVR_px,
+
     /// SS or US depending on context
     EVR_xs,
 
index 17d046d8955572231c2a5abe33eab088819d9565..d86a0c0721a8964cd8aefbe005709d43ace83b37 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -159,7 +159,7 @@ class DCMTK_DCMDATA_EXPORT DcmAttributeTag
      *  @param format used to format and customize the output
      *  @return status, EC_Normal if successful, an error code otherwise
      */
-    OFCondition writeJson(STD_NAMESPACE ostream &out,
+    virtual OFCondition writeJson(STD_NAMESPACE ostream &out,
                           DcmJsonFormat &format);
 
     /** get particular tag value
index f7ea5006666be1009b1f9e4f1713e3050786ea31..14d4a100bd971c9d0a7651c836167e7485b9411b 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2016, OFFIS e.V.
+ *  Copyright (C) 1994-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -128,6 +128,30 @@ class DCMTK_DCMDATA_EXPORT DcmDecimalString
                                     const unsigned long pos,
                                     OFBool normalize = OFTrue);
 
+    /** put particular float value at a specific position. Precision (number of digits
+     *  in fractional part) is 6. However, trailing zeroes from fractional part will be removed
+     *  in every case.
+     *  @param val the floating point value to put
+     *  @param pos index where to put the value (0..vm-1)
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition putFloat64(const Float64 val,
+                                   const unsigned long pos = 0);
+
+    /** put particular float value at a specific position, using a particular
+     *  precision (number of digits in fractional part).
+     *  @param val the floating point value to put
+     *  @param pos index where to put the value (0..vm-1)
+     *  @param prec precision to be used, i.e. maximum number of fractional digits.
+     *         Value should be 0 < prec < 15 (positive val) or 0 < prec < 14 (negative).
+     *  @param cutTrailZeroes If OFTrue, any trailing non-significant zeroes are removed (from fraction).
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition putFloat64Prec(const Float64 val,
+                                       const unsigned long pos = 0,
+                                       const Uint8 prec = 6,
+                                       const OFBool cutTrailZeroes = OFTrue);
+
     /** write object in XML format
      *  @param out output stream to which the XML document is written
      *  @param flags optional flag used to customize the output (see DCMTypes::XF_xxx)
index 737447c03213b12a47908020cada8bb3f52447ca..c656a6d6efa75cbc89c51780c8aef95acfce568f 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -27,6 +27,9 @@
 
 #include "dcmtk/dcmdata/dcelem.h"
 
+// forward declarations
+class DcmJsonFormat;
+
 
 /** a class representing the DICOM value representation 'Floating Point Double' (FD)
  */
@@ -214,6 +217,14 @@ class DCMTK_DCMDATA_EXPORT DcmFloatingPointDouble
     virtual OFBool matches(const DcmElement& candidate,
                            const OFBool enableWildCardMatching = OFTrue) const;
 
+    /** write object in JSON format
+     *  @param out output stream to which the JSON document is written
+     *  @param format used to format and customize the output
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition writeJson(STD_NAMESPACE ostream &out,
+                                  DcmJsonFormat &format);
+
   protected:
 
     /** constructor. Create new element from given tag and length.
index fc4756cb48ad7cbf732b0f1709ab239006bae8cf..65e59c0e357c3d4e46a6bc13dec2a6301a11babf 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -27,6 +27,8 @@
 
 #include "dcmtk/dcmdata/dcelem.h"
 
+// forward declarations
+class DcmJsonFormat;
 
 /** a class representing the DICOM value representation 'Floating Point Single' (FL)
  */
@@ -216,6 +218,14 @@ class DCMTK_DCMDATA_EXPORT DcmFloatingPointSingle
     virtual OFBool matches(const DcmElement& candidate,
                            const OFBool enableWildCardMatching = OFTrue) const;
 
+    /** write object in JSON format
+     *  @param out output stream to which the JSON document is written
+     *  @param format used to format and customize the output
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition writeJson(STD_NAMESPACE ostream &out,
+                                  DcmJsonFormat &format);
+
   protected:
 
     /** constructor. Create new element from given tag and length.
index 3854f1d6dc427085080ac3cfe30279a8c5780ca3..0fb0e51e6685ab85bf2317eb684bcedb1d02f690 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2017, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -133,7 +133,7 @@ class DCMTK_DCMDATA_EXPORT DcmIntegerString
      *  @param format used to format and customize the output
      *  @return status, EC_Normal if successful, an error code otherwise
      */
-    OFCondition writeJson(STD_NAMESPACE ostream &out,
+    virtual OFCondition writeJson(STD_NAMESPACE ostream &out,
                           DcmJsonFormat &format);
 };
 
index 751f29a863d6b4f7b243b80a1e25cfd11f01f9af..21ff617e041e69d2765ba763a2f2aa1ae2dbd6df 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2017, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -183,7 +183,7 @@ class DCMTK_DCMDATA_EXPORT DcmPersonName
      *  @param format used to format and customize the output
      *  @return status, EC_Normal if successful, an error code otherwise
      */
-    OFCondition writeJson(STD_NAMESPACE ostream &out,
+    virtual OFCondition writeJson(STD_NAMESPACE ostream &out,
                           DcmJsonFormat &format);
 
     /* --- static helper functions --- */
index ae81fe6619cda0b4be806c53cd2c407c3d6935f3..8c88f0928ada81c6a0c5eff29a70d00446e51e10 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2019, OFFIS e.V.
+ *  Copyright (C) 2019-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -209,6 +209,14 @@ class DCMTK_DCMDATA_EXPORT DcmSigned64bitVeryLong
      */
     virtual OFCondition verify(const OFBool autocorrect = OFFalse);
 
+    /** write object in JSON format
+     *  @param out output stream to which the JSON document is written
+     *  @param format used to format and customize the output
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition writeJson(STD_NAMESPACE ostream &out,
+                                  DcmJsonFormat &format);
+
   protected:
 
     /** constructor. Create new element from given tag and length.
index 04db9bd84e6fe8411cedec89cc1334ee1417a76c..407f7e656aa9a9f4c15993257f5ffcb679d3e94c 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2019, OFFIS e.V.
+ *  Copyright (C) 2019-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -27,7 +27,6 @@
 
 #include "dcmtk/dcmdata/dcelem.h"
 
-
 /** a class representing the DICOM value representation 'Unsigned 64-bit Very Long' (UV)
  */
 class DCMTK_DCMDATA_EXPORT DcmUnsigned64bitVeryLong
@@ -209,6 +208,14 @@ class DCMTK_DCMDATA_EXPORT DcmUnsigned64bitVeryLong
      */
     virtual OFCondition verify(const OFBool autocorrect = OFFalse);
 
+    /** write object in JSON format
+     *  @param out output stream to which the JSON document is written
+     *  @param format used to format and customize the output
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition writeJson(STD_NAMESPACE ostream &out,
+                                  DcmJsonFormat &format);
+
   protected:
 
     /** constructor. Create new element from given tag and length.
index cb1fb08ac412946c5437831811c4142562aba194..abc92a187581c53803ec4e4ef77701b9e4279459 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2001-2011, OFFIS e.V.
+ *  Copyright (C) 2001-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -43,6 +43,8 @@ public:
    *  @param inputPlug - [in] The input plugin to read pixel data
    *  @param outPlug - [in] The output plugin for specific SOP class output
    *  @param resultDset - [out] The DICOM object resulting from the conversion
+   *         The dataset is allocated in this method and must be freed by the
+   *         caller.
    *  @param proposedTS - [out] The proposed transfer syntax (needed e. g.
    *                            by JPEG input plugin)
    *  @return EC_Normal, if successfull, error otherwise
index 8a65fed0f3007aa7ef6a9a2042e7594d249aa297..0c966a449982b70e0e920beb107d66c3b7408c5c 100644 (file)
@@ -826,30 +826,34 @@ OFCondition I2DJpegSource::skipVariable()
 
 OFCondition I2DJpegSource::isJPEGEncodingSupported(const E_JPGMARKER& jpegEncoding) const
 {
+  OFCondition result;
   DCMDATA_LIBI2D_DEBUG("I2DJpegSource: Checking whether JPEG encoding is supported");
   DCMDATA_LIBI2D_DEBUG("I2DJpegSource:   Encoding: " << jpegMarkerToString(jpegEncoding));
   switch (jpegEncoding)
   {
     case E_JPGMARKER_SOF0: // Baseline
-      return EC_Normal;
+      result = EC_Normal;
+      break;
     case E_JPGMARKER_SOF1: // Extended sequential
       if (!m_disableExtSeqTs)
-        return EC_Normal;
+        result = EC_Normal;
       else
-        return makeOFCondition(OFM_dcmdata, 18, OF_error, "Unable to convert: Extended sequential JPEG coding found but support disabled");
+        result = makeOFCondition(OFM_dcmdata, 18, OF_error, "Unable to convert: Extended sequential JPEG coding found but support disabled");
+      break;
     case E_JPGMARKER_SOF2: // Progressive
       if (!m_disableProgrTs)
-        return EC_Normal;
+        result = EC_Normal;
       else
-        return makeOFCondition(OFM_dcmdata, 18, OF_error, "Unable to convert: Progressive JPEG coding found but disabled");
+        result = makeOFCondition(OFM_dcmdata, 18, OF_error, "Unable to convert: Progressive JPEG coding found but disabled");
+      break;
     // SOF3: Lossless, SOF5-7: Hierarchical (differential), SOF9-15: Arithmetic coding, all other
     default:
       OFString errMsg("JPEG data with encoding: '");
       errMsg += jpegMarkerToString(jpegEncoding);
       errMsg += "' not supported";
-      return makeOFCondition(OFM_dcmdata, 18, OF_error, errMsg.c_str());
+      result = makeOFCondition(OFM_dcmdata, 18, OF_error, errMsg.c_str());
   }
-  return EC_Normal;
+  return result;
 }
 
 
index b8fa0b1ccebe0f8a6edd57440d2371562af3b4ee..3d550bdea5cedb285200174b2559073ce9e7535a 100644 (file)
@@ -475,6 +475,91 @@ OFCondition DcmByteString::putString(const char *stringVal,
 }
 
 
+OFCondition DcmByteString::putOFStringAtPos(const OFString& stringVal,
+                                            const unsigned long pos)
+{
+    OFCondition result;
+    // Get old value
+    OFString str;
+    result = getOFStringArray( str );
+    if (result.good())
+    {
+        size_t currentVM = getNumberOfValues();
+        // Trivial case: No values are set and new value should go to first position
+        if ( (currentVM == 0) && (pos == 0))
+            return putOFStringArray(stringVal);
+
+        // 1st case: Insert at the end
+        // If we insert at a position that does not yet exist, append missing number of components by
+        // adding the corresponding number of backspace chars, append new float value and return.
+        size_t futureVM = pos + 1;
+        if (futureVM > currentVM)
+        {
+            str = str.append(currentVM == 0 ? futureVM - currentVM - 1 : futureVM - currentVM, '\\');
+            str = str.append(stringVal);
+            return putOFStringArray(str);
+        }
+
+        // 2nd case: New value should be at position 0
+        size_t rightPos = 0;
+        if (pos == 0)
+        {
+            // First value is empty: Insert new value
+            if (str[0] == '\\')
+            {
+                str = str.insert(0, stringVal);
+            }
+            // First value is set: Replace old value with new value
+            else
+            {
+                rightPos = str.find_first_of('\\', 0);
+                str = str.replace(0, rightPos, stringVal);
+            }
+            return putOFStringArray(str);
+        }
+
+        // 3rd case: New value should be inserted somewhere in the middle
+        size_t leftPos = 0;
+        size_t vmPos = 0;
+        // First, find the correct position, and then insert / replace new value
+        do
+        {
+            // Step from value to value by looking for delimiters.
+            // Special handling first search (start looking at position 0 instead of 1)
+            if (vmPos == 0) leftPos = str.find('\\', 0);
+            else leftPos = str.find('\\', leftPos + 1 );
+            // leftPos = str.find('\\', leftPos == 0 ? 0 : leftPos +1);
+            if (leftPos != OFString_npos)
+            {
+                vmPos++;
+            }
+        }
+        while ( (leftPos != OFString_npos) && (vmPos != pos) );
+        rightPos = str.find_first_of('\\', leftPos+1);
+        if (rightPos == OFString_npos) rightPos = str.length();
+
+        // If we do not have an old value of size 1 or we have an empty value
+        if (rightPos - leftPos == 1)
+        {
+            // Empty value
+            if (str.at(leftPos) == '\\')
+                str = str.insert(rightPos, stringVal);
+            // Old value (length 1)
+            else
+                str = str.replace(leftPos, 1, stringVal);
+        }
+        // Otherwise replace existing old value (length > 1)
+        else
+        {
+            str = str.replace(leftPos+1, rightPos - leftPos, stringVal);
+        }
+        // Finally re-insert all values include new value
+        result = putOFStringArray( str );
+    }
+    return result;
+}
+
+
 // ********************************
 
 
index bb32f38853f7fb25f83d6477417f68763da4ee6e..52d6a2a70f6045812c33b1d48d06f28aa77c6197 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1997-2016, OFFIS e.V.
+ *  Copyright (C) 1997-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -434,7 +434,8 @@ OFCondition DcmCodecList::decode(
   const DcmRepresentationParameter * fromParam,
   DcmPixelSequence * fromPixSeq,
   DcmPolymorphOBOW& uncompressedPixelData,
-  DcmStack & pixelStack)
+  DcmStack & pixelStack,
+  OFBool& removeOldRep)
 {
 #ifdef WITH_THREADS
   if (! codecLock.initialized()) return EC_IllegalCall; // should never happen
@@ -454,7 +455,7 @@ OFCondition DcmCodecList::decode(
     {
       if ((*first)->codec->canChangeCoding(fromXfer, EXS_LittleEndianExplicit))
       {
-        result = (*first)->codec->decode(fromParam, fromPixSeq, uncompressedPixelData, (*first)->codecParameter, pixelStack);
+        result = (*first)->codec->decode(fromParam, fromPixSeq, uncompressedPixelData, (*first)->codecParameter, pixelStack, removeOldRep);
         first = last;
       } else ++first;
     }
@@ -513,7 +514,8 @@ OFCondition DcmCodecList::encode(
   const E_TransferSyntax toRepType,
   const DcmRepresentationParameter * toRepParam,
   DcmPixelSequence * & toPixSeq,
-  DcmStack & pixelStack)
+  DcmStack & pixelStack,
+  OFBool& removeOldRep)
 {
   toPixSeq = NULL;
 #ifdef WITH_THREADS
@@ -535,7 +537,7 @@ OFCondition DcmCodecList::encode(
       {
         if (!toRepParam) toRepParam = (*first)->defaultRepParam;
         result = (*first)->codec->encode(fromRepType, fromParam, fromPixSeq,
-                 toRepParam, toPixSeq, (*first)->codecParameter, pixelStack);
+                 toRepParam, toPixSeq, (*first)->codecParameter, pixelStack, removeOldRep);
         first = last;
       } else ++first;
     }
@@ -553,7 +555,8 @@ OFCondition DcmCodecList::encode(
   const E_TransferSyntax toRepType,
   const DcmRepresentationParameter * toRepParam,
   DcmPixelSequence * & toPixSeq,
-  DcmStack & pixelStack)
+  DcmStack & pixelStack,
+  OFBool& removeOldRep)
 {
   toPixSeq = NULL;
 #ifdef WITH_THREADS
@@ -575,7 +578,7 @@ OFCondition DcmCodecList::encode(
       {
         if (!toRepParam) toRepParam = (*first)->defaultRepParam;
         result = (*first)->codec->encode(pixelData, length, toRepParam, toPixSeq,
-                 (*first)->codecParameter, pixelStack);
+                 (*first)->codecParameter, pixelStack, removeOldRep);
         first = last;
       } else ++first;
     }
index 3b8a3dd19a40d2b339821fac01d4167d8736a143..3128b47c50a121a9148b6b95919cb17341821a0b 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -343,21 +343,7 @@ OFCondition DcmDataset::writeXML(STD_NAMESPACE ostream &out,
 OFCondition DcmDataset::writeJson(STD_NAMESPACE ostream &out,
                                   DcmJsonFormat &format)
 {
-    // write dataset content
-    if (!elementList->empty())
-    {
-        elementList->seek(ELP_first);
-        OFCondition status = EC_Normal;
-        // write content of all children
-        status = elementList->get()->writeJson(out, format);
-        while (status.good() && elementList->seek(ELP_next))
-        {
-            out << "," << format.newline();
-            status = elementList->get()->writeJson(out, format);
-        }
-        return status;
-    }
-    return EC_Normal;
+    return writeJsonExt(out, format, OFFalse, OFFalse); // omit braces
 }
 
 
index da28585332e99a7b1ae38372bf03fe1176fa7b8d..8937cbe30a0c6d3d166f2cdd7b198f51623dc76a 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2002-2019, OFFIS e.V.
+ *  Copyright (C) 2002-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -697,7 +697,13 @@ static E_DirRecType sopClassToRecordType(const OFString &sopClass)
              compare(sopClass, UID_BasicVoiceAudioWaveformStorage) ||
              compare(sopClass, UID_GeneralAudioWaveformStorage) ||
              compare(sopClass, UID_ArterialPulseWaveformStorage) ||
-             compare(sopClass, UID_RespiratoryWaveformStorage))
+             compare(sopClass, UID_RespiratoryWaveformStorage) ||
+             compare(sopClass, UID_RoutineScalpElectroencephalogramWaveformStorage) ||
+             compare(sopClass, UID_ElectromyogramWaveformStorage) ||
+             compare(sopClass, UID_ElectrooculogramWaveformStorage) ||
+             compare(sopClass, UID_SleepElectroencephalogramWaveformStorage) ||
+             compare(sopClass, UID_MultichannelRespiratoryWaveformStorage) ||
+             compare(sopClass, UID_BodyPositionWaveformStorage))
     {
         result = ERT_Waveform;
     }
@@ -734,7 +740,9 @@ static E_DirRecType sopClassToRecordType(const OFString &sopClass)
         result = ERT_Spectroscopy;
     else if (compare(sopClass, UID_EncapsulatedPDFStorage) ||
              compare(sopClass, UID_EncapsulatedCDAStorage) ||
-             compare(sopClass, UID_EncapsulatedSTLStorage))
+             compare(sopClass, UID_EncapsulatedSTLStorage) ||
+             compare(sopClass, UID_EncapsulatedOBJStorage) ||
+             compare(sopClass, UID_EncapsulatedMTLStorage))
     {
         result = ERT_EncapDoc;
     }
@@ -782,7 +790,14 @@ static E_DirRecType sopClassToRecordType(const OFString &sopClass)
     else if (compare(sopClass, UID_RTPhysicianIntentStorage) ||
              compare(sopClass, UID_RTSegmentAnnotationStorage) ||
              compare(sopClass, UID_RTRadiationSetStorage) ||
-             compare(sopClass, UID_CArmPhotonElectronRadiationStorage))
+             compare(sopClass, UID_CArmPhotonElectronRadiationStorage) ||
+             compare(sopClass, UID_TomotherapeuticRadiationStorage) ||
+             compare(sopClass, UID_RoboticArmRadiationStorage) ||
+             compare(sopClass, UID_RTRadiationRecordSetStorage) ||
+             compare(sopClass, UID_RTRadiationSalvageRecordStorage) ||
+             compare(sopClass, UID_TomotherapeuticRadiationRecordStorage) ||
+             compare(sopClass, UID_CArmPhotonElectronRadiationRecordStorage) ||
+             compare(sopClass, UID_RoboticRadiationRecordStorage))
     {
         result = ERT_Radiotherapy;
     }
@@ -1605,7 +1620,13 @@ OFCondition DicomDirInterface::checkSOPClassAndXfer(DcmMetaInfo *metainfo,
                                 compare(mediaSOPClassUID, UID_BasicVoiceAudioWaveformStorage) ||
                                 compare(mediaSOPClassUID, UID_GeneralAudioWaveformStorage) ||
                                 compare(mediaSOPClassUID, UID_ArterialPulseWaveformStorage) ||
-                                compare(mediaSOPClassUID, UID_RespiratoryWaveformStorage);
+                                compare(mediaSOPClassUID, UID_RespiratoryWaveformStorage) ||
+                                compare(mediaSOPClassUID, UID_MultichannelRespiratoryWaveformStorage) ||
+                                compare(mediaSOPClassUID, UID_RoutineScalpElectroencephalogramWaveformStorage) ||
+                                compare(mediaSOPClassUID, UID_ElectromyogramWaveformStorage) ||
+                                compare(mediaSOPClassUID, UID_ElectrooculogramWaveformStorage) ||
+                                compare(mediaSOPClassUID, UID_SleepElectroencephalogramWaveformStorage) ||
+                                compare(mediaSOPClassUID, UID_BodyPositionWaveformStorage);
                     }
                     /* is it one of the presentation state SOP Classes? */
                     if (!found)
@@ -2577,16 +2598,22 @@ OFCondition DicomDirInterface::checkMandatoryAttributes(DcmMetaInfo *metainfo,
                         OFString tmpString;
                         if (compare(getStringFromDataset(dataset, DCM_VerificationFlag, tmpString), "VERIFIED"))
                         {
-                            /* VerificationDateTime is required if verification flag is VERIFIED,
-                               retrieve most recent (= last) entry from VerifyingObserverSequence */
-                            DcmItem *ditem = NULL;
-                            OFCondition l_status = dataset->findAndGetSequenceItem(DCM_VerifyingObserverSequence, ditem, -1 /*last*/);
-                            if (l_status.good())
+                            if (checkExistsWithValue(dataset, DCM_VerifyingObserverSequence, filename))
                             {
-                                if (!checkExistsWithValue(ditem, DCM_VerificationDateTime, filename))
-                                    result = EC_MissingAttribute;
+                                /* VerificationDateTime is required if VerificationFlag is VERIFIED,
+                                   retrieve most recent (= last) entry from VerifyingObserverSequence */
+                                DcmItem *ditem = NULL;
+                                if (dataset->findAndGetSequenceItem(DCM_VerifyingObserverSequence, ditem, -1 /*last*/).good())
+                                {
+                                    if (!checkExistsWithValue(ditem, DCM_VerificationDateTime, filename))
+                                        result = EC_MissingAttribute;
+                                } else {
+                                    /* should never happen */
+                                    DCMDATA_ERROR("INTERNAL ERROR: cannot get last item of VerifyingObserverSequence");
+                                    result = EC_InternalError;
+                                }
                             } else
-                                result = l_status;
+                                result = EC_MissingAttribute;
                         }
                     }
                     break;
@@ -3300,7 +3327,7 @@ DcmDirectoryRecord *DicomDirInterface::buildStructReportRecord(DcmDirectoryRecor
             copyElementType1(dataset, DCM_ContentTime, record, sourceFilename);
             if (compare(getStringFromDataset(dataset, DCM_VerificationFlag, tmpString), "VERIFIED"))
             {
-                /* VerificationDateTime is required if verification flag is VERIFIED,
+                /* VerificationDateTime is required if VerificationFlag is VERIFIED,
                    retrieve most recent (= last) entry from VerifyingObserverSequence */
                 DcmItem *ditem = NULL;
                 OFCondition status = dataset->findAndGetSequenceItem(DCM_VerifyingObserverSequence, ditem, -1 /*last*/);
index e757906c8f9100559c3fe3fc5a7758a131074f37..57e30a45672b7450a795406e84190115e8a7ad5f 100644 (file)
@@ -4,7 +4,7 @@
 **
 **   User: joergr
 **   Host: thinkpad
-**   Date: 2019-08-07 18:58:15
+**   Date: 2020-11-24 14:49:53
 **   Prog: /home/joergr/Source/dcmtk-full/public/dcmdata/libsrc/mkdictbi
 **
 **   From: ../data/dicom.dic
@@ -256,6 +256,46 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       EVR_AE, "ReceivingApplicationEntityTitle", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
+  , { 0x0002, 0x0026, 0x0002, 0x0026,
+      EVR_UR, "SourcePresentationAddress", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0002, 0x0027, 0x0002, 0x0027,
+      EVR_UR, "SendingPresentationAddress", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0002, 0x0028, 0x0002, 0x0028,
+      EVR_UR, "ReceivingPresentationAddress", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0002, 0x0031, 0x0002, 0x0031,
+      EVR_OB, "RTVMetaInformationVersion", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0002, 0x0032, 0x0002, 0x0032,
+      EVR_UI, "RTVCommunicationSOPClassUID", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0002, 0x0033, 0x0002, 0x0033,
+      EVR_UI, "RTVCommunicationSOPInstanceUID", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0002, 0x0035, 0x0002, 0x0035,
+      EVR_OB, "RTVSourceIdentifier", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0002, 0x0036, 0x0002, 0x0036,
+      EVR_OB, "RTVFlowIdentifier", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0002, 0x0037, 0x0002, 0x0037,
+      EVR_UL, "RTVFlowRTPSamplingRate", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0002, 0x0038, 0x0002, 0x0038,
+      EVR_FD, "RTVFlowActualFrameDuration", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
   , { 0x0002, 0x0100, 0x0002, 0x0100,
       EVR_UI, "PrivateInformationCreatorUID", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
@@ -384,6 +424,10 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       "AEGIS_DICOM_2.00" }
 #endif
+  , { 0x0006, 0x0001, 0x0006, 0x0001,
+      EVR_SQ, "CurrentFrameFunctionalGroupsSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
   , { 0x0008, 0x0001, 0x0008, 0x0001,
       EVR_UL, "RETIRED_LengthToEnd", 1, 1, "DICOM/retired",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
@@ -1160,6 +1204,10 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       EVR_SQ, "AlternateRepresentationSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
+  , { 0x0008, 0x3002, 0x0008, 0x3002,
+      EVR_UI, "AvailableTransferSyntaxUID", 1, -1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
   , { 0x0008, 0x3010, 0x0008, 0x3010,
       EVR_UI, "IrradiationEventUID", 1, -1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
@@ -4196,6 +4244,26 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       EVR_IS, "GPSDifferential", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
+  , { 0x0016, 0x1001, 0x0016, 0x1001,
+      EVR_CS, "LightSourcePolarization", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0016, 0x1002, 0x0016, 0x1002,
+      EVR_DS, "EmitterColorTemperature", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0016, 0x1003, 0x0016, 0x1003,
+      EVR_CS, "ContactMethod", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0016, 0x1004, 0x0016, 0x1004,
+      EVR_CS, "ImmersionMedia", 1, -1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0016, 0x1005, 0x0016, 0x1005,
+      EVR_DS, "OpticalMagnificationFactor", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
 #ifdef ENABLE_PRIVATE_TAGS
   , { 0x0017, 0x0000, 0x0017, 0x0000,
       EVR_LO, "ExtendedBodyPart", 1, 1, "PrivateTag",
@@ -4459,7 +4527,7 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x0018, 0x100b, 0x0018, 0x100b,
-      EVR_UI, "ManufacturerDeviceClassUID", 1, -1, "DICOM/Supplement_175",
+      EVR_UI, "ManufacturerDeviceClassUID", 1, -1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x0018, 0x1010, 0x0018, 0x1010,
@@ -5131,39 +5199,39 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x0018, 0x1630, 0x0018, 0x1630,
-      EVR_CS, "OutlineShapeType", 1, 1, "DICOM/Supplement_175",
+      EVR_CS, "OutlineShapeType", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x0018, 0x1631, 0x0018, 0x1631,
-      EVR_FD, "OutlineLeftVerticalEdge", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "OutlineLeftVerticalEdge", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x0018, 0x1632, 0x0018, 0x1632,
-      EVR_FD, "OutlineRightVerticalEdge", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "OutlineRightVerticalEdge", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x0018, 0x1633, 0x0018, 0x1633,
-      EVR_FD, "OutlineUpperHorizontalEdge", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "OutlineUpperHorizontalEdge", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x0018, 0x1634, 0x0018, 0x1634,
-      EVR_FD, "OutlineLowerHorizontalEdge", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "OutlineLowerHorizontalEdge", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x0018, 0x1635, 0x0018, 0x1635,
-      EVR_FD, "CenterOfCircularOutline", 2, 2, "DICOM/Supplement_175",
+      EVR_FD, "CenterOfCircularOutline", 2, 2, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x0018, 0x1636, 0x0018, 0x1636,
-      EVR_FD, "DiameterOfCircularOutline", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "DiameterOfCircularOutline", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x0018, 0x1637, 0x0018, 0x1637,
-      EVR_UL, "NumberOfPolygonalVertices", 1, 1, "DICOM/Supplement_175",
+      EVR_UL, "NumberOfPolygonalVertices", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x0018, 0x1638, 0x0018, 0x1638,
-      EVR_OF, "VerticesOfThePolygonalOutline", 1, 1, "DICOM/Supplement_175",
+      EVR_OF, "VerticesOfThePolygonalOutline", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x0018, 0x1700, 0x0018, 0x1700,
@@ -5310,6 +5378,10 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       EVR_LO, "TransducerData", 1, -1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
+  , { 0x0018, 0x5011, 0x0018, 0x5011,
+      EVR_SQ, "TransducerIdentificationSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
   , { 0x0018, 0x5012, 0x0018, 0x5012,
       EVR_DS, "FocusDepth", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
@@ -18189,6 +18261,56 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       EVR_LT, "PatientStudyUID", 1, 1, "PrivateTag",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       "SIEMENS RIS" }
+#endif
+  , { 0x0034, 0x0001, 0x0034, 0x0001,
+      EVR_SQ, "FlowIdentifierSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0034, 0x0002, 0x0034, 0x0002,
+      EVR_OB, "FlowIdentifier", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0034, 0x0003, 0x0034, 0x0003,
+      EVR_UI, "FlowTransferSyntaxUID", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0034, 0x0004, 0x0034, 0x0004,
+      EVR_UL, "FlowRTPSamplingRate", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0034, 0x0005, 0x0034, 0x0005,
+      EVR_OB, "SourceIdentifier", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0034, 0x0007, 0x0034, 0x0007,
+      EVR_OB, "FrameOriginTimestamp", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0034, 0x0008, 0x0034, 0x0008,
+      EVR_CS, "IncludesImagingSubject", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0034, 0x0009, 0x0034, 0x0009,
+      EVR_SQ, "FrameUsefulnessGroupSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0034, 0x000a, 0x0034, 0x000a,
+      EVR_SQ, "RealTimeBulkDataFlowSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0034, 0x000b, 0x0034, 0x000b,
+      EVR_SQ, "CameraPositionGroupSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0034, 0x000c, 0x0034, 0x000c,
+      EVR_CS, "IncludesInformation", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0034, 0x000d, 0x0034, 0x000d,
+      EVR_SQ, "TimeOfFrameGroupSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+#ifdef ENABLE_PRIVATE_TAGS
   , { 0x0037, 0x0010, 0x0037, 0x0010,
       EVR_LO, "ReferringDepartment", 1, 1, "PrivateTag",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
@@ -18508,6 +18630,34 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       EVR_CS, "ChannelMode", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
+  , { 0x003a, 0x0310, 0x003a, 0x0310,
+      EVR_UI, "MultiplexGroupUID", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x003a, 0x0311, 0x003a, 0x0311,
+      EVR_DS, "PowerlineFrequency", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x003a, 0x0312, 0x003a, 0x0312,
+      EVR_SQ, "ChannelImpedanceSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x003a, 0x0313, 0x003a, 0x0313,
+      EVR_DS, "ImpedanceValue", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x003a, 0x0314, 0x003a, 0x0314,
+      EVR_DT, "ImpedanceMeasurementDateTime", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x003a, 0x0315, 0x003a, 0x0315,
+      EVR_DS, "ImpedanceMeasurementFrequency", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x003a, 0x0316, 0x003a, 0x0316,
+      EVR_CS, "ImpedanceMeasurementCurrentType", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
   , { 0x0040, 0x0001, 0x0040, 0x0001,
       EVR_AE, "ScheduledStationAETitle", 1, -1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
@@ -19692,6 +19842,38 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       EVR_SQ, "RETIRED_LanguageCodeSequenceTrial", 1, 1, "DICOM/retired",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
+  , { 0x0040, 0xa801, 0x0040, 0xa801,
+      EVR_SQ, "TabulatedValuesSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0040, 0xa802, 0x0040, 0xa802,
+      EVR_UL, "NumberOfTableRows", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0040, 0xa803, 0x0040, 0xa803,
+      EVR_UL, "NumbeOfTableColumns", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0040, 0xa804, 0x0040, 0xa804,
+      EVR_UL, "TableRowNumber", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0040, 0xa805, 0x0040, 0xa805,
+      EVR_UL, "TableColumnNumber", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0040, 0xa806, 0x0040, 0xa806,
+      EVR_SQ, "TableRowDefinitionSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0040, 0xa807, 0x0040, 0xa807,
+      EVR_SQ, "TableColumnDefinitionSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0040, 0xa808, 0x0040, 0xa808,
+      EVR_SQ, "CellValuesSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
   , { 0x0040, 0xa992, 0x0040, 0xa992,
       EVR_ST, "RETIRED_UniformResourceLocatorTrial", 1, 1, "DICOM/retired",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
@@ -22628,6 +22810,14 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       EVR_SQ, "ModelUsageCodeSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
+  , { 0x0068, 0x7004, 0x0068, 0x7004,
+      EVR_UI, "ModelGroupUID", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0068, 0x7005, 0x0068, 0x7005,
+      EVR_UR, "RelativeURIReferenceWithinEncapsulatedDocument", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
   , { 0x0070, 0x0001, 0x0070, 0x0001,
       EVR_SQ, "GraphicAnnotationSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
@@ -23608,6 +23798,18 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       EVR_SQ, "SelectorCodeSequenceValue", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
+  , { 0x0072, 0x0081, 0x0072, 0x0081,
+      EVR_OV, "SelectorOVValue", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0072, 0x0082, 0x0072, 0x0082,
+      EVR_SV, "SelectorSVValue", 1, -1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x0072, 0x0083, 0x0072, 0x0083,
+      EVR_UV, "SelectorUVValue", 1, -1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
   , { 0x0072, 0x0100, 0x0072, 0x0100,
       EVR_US, "NumberOfScreens", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
@@ -26191,15 +26393,15 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x3006, 0x00c9, 0x3006, 0x00c9,
-      EVR_SQ, "PatientLocationCoordinatesSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "PatientLocationCoordinatesSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x3006, 0x00ca, 0x3006, 0x00ca,
-      EVR_SQ, "PatientLocationCoordinatesCodeSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "PatientLocationCoordinatesCodeSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x3006, 0x00cb, 0x3006, 0x00cb,
-      EVR_SQ, "PatientSupportPositionSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "PatientSupportPositionSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x3008, 0x0010, 0x3008, 0x0010,
@@ -26799,7 +27001,7 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0082, 0x300a, 0x0082,
-      EVR_DS, "BeamDoseSpecificationPoint", 3, 3, "DICOM",
+      EVR_DS, "RETIRED_BeamDoseSpecificationPoint", 3, 3, "DICOM/retired",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0083, 0x300a, 0x0083,
@@ -28006,6 +28208,10 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       EVR_FL, "ScanningSpotSize", 2, 2, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
+  , { 0x300a, 0x0399, 0x300a, 0x0399,
+      EVR_FL, "ScanSpotSizesDelivered", 2, -1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
   , { 0x300a, 0x039a, 0x300a, 0x039a,
       EVR_IS, "NumberOfPaintings", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
@@ -28078,6 +28284,10 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       EVR_FL, "SourceToGeneralAccessoryDistance", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
+  , { 0x300a, 0x0426, 0x300a, 0x0426,
+      EVR_DS, "IsocenterToGeneralAccessoryDistance", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
   , { 0x300a, 0x0431, 0x300a, 0x0431,
       EVR_SQ, "ApplicatorGeometrySequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
@@ -28183,551 +28393,719 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0600, 0x300a, 0x0600,
-      EVR_US, "RTControlPointIndex", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "RTControlPointIndex", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0601, 0x300a, 0x0601,
-      EVR_US, "RadiationGenerationModeIndex", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "RadiationGenerationModeIndex", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0602, 0x300a, 0x0602,
-      EVR_US, "ReferencedDefinedDeviceIndex", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "ReferencedDefinedDeviceIndex", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0603, 0x300a, 0x0603,
-      EVR_US, "RadiationDoseIdentificationIndex", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "RadiationDoseIdentificationIndex", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0604, 0x300a, 0x0604,
-      EVR_US, "NumberOfRTControlPoints", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "NumberOfRTControlPoints", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0605, 0x300a, 0x0605,
-      EVR_US, "ReferencedRadiationGenerationModeIndex", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "ReferencedRadiationGenerationModeIndex", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0606, 0x300a, 0x0606,
-      EVR_US, "TreatmentPositionIndex", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "TreatmentPositionIndex", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0607, 0x300a, 0x0607,
-      EVR_US, "ReferencedDeviceIndex", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "ReferencedDeviceIndex", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0608, 0x300a, 0x0608,
-      EVR_LO, "TreatmentPositionGroupLabel", 1, 1, "DICOM/Supplement_175",
+      EVR_LO, "TreatmentPositionGroupLabel", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0609, 0x300a, 0x0609,
-      EVR_UI, "TreatmentPositionGroupUID", 1, 1, "DICOM/Supplement_175",
+      EVR_UI, "TreatmentPositionGroupUID", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x060a, 0x300a, 0x060a,
-      EVR_SQ, "TreatmentPositionGroupSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "TreatmentPositionGroupSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x060b, 0x300a, 0x060b,
-      EVR_US, "ReferencedTreatmentPositionIndex", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "ReferencedTreatmentPositionIndex", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x060c, 0x300a, 0x060c,
-      EVR_US, "ReferencedRadiationDoseIdentificationIndex", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "ReferencedRadiationDoseIdentificationIndex", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x060d, 0x300a, 0x060d,
-      EVR_FD, "RTAccessoryHolderWaterEquivalentThickness", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "RTAccessoryHolderWaterEquivalentThickness", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x060e, 0x300a, 0x060e,
-      EVR_US, "ReferencedRTAccessoryHolderDeviceIndex", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "ReferencedRTAccessoryHolderDeviceIndex", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x060f, 0x300a, 0x060f,
-      EVR_CS, "RTAccessoryHolderSlotExistenceFlag", 1, 1, "DICOM/Supplement_175",
+      EVR_CS, "RTAccessoryHolderSlotExistenceFlag", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0610, 0x300a, 0x0610,
-      EVR_SQ, "RTAccessoryHolderSlotSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "RTAccessoryHolderSlotSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0611, 0x300a, 0x0611,
-      EVR_LO, "RTAccessoryHolderSlotID", 1, 1, "DICOM/Supplement_175",
+      EVR_LO, "RTAccessoryHolderSlotID", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0612, 0x300a, 0x0612,
-      EVR_FD, "RTAccessoryHolderSlotDistance", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "RTAccessoryHolderSlotDistance", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0613, 0x300a, 0x0613,
-      EVR_FD, "RTAccessorySlotDistance", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "RTAccessorySlotDistance", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0614, 0x300a, 0x0614,
-      EVR_SQ, "RTAccessoryHolderDefinitionSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "RTAccessoryHolderDefinitionSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0615, 0x300a, 0x0615,
-      EVR_LO, "RTAccessoryDeviceSlotID", 1, 1, "DICOM/Supplement_175",
+      EVR_LO, "RTAccessoryDeviceSlotID", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0616, 0x300a, 0x0616,
-      EVR_SQ, "RTRadiationSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "RTRadiationSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0617, 0x300a, 0x0617,
-      EVR_SQ, "RadiationDoseSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "RadiationDoseSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0618, 0x300a, 0x0618,
-      EVR_SQ, "RadiationDoseIdentificationSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "RadiationDoseIdentificationSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0619, 0x300a, 0x0619,
-      EVR_LO, "RadiationDoseIdentificationLabel", 1, 1, "DICOM/Supplement_175",
+      EVR_LO, "RadiationDoseIdentificationLabel", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x061a, 0x300a, 0x061a,
-      EVR_CS, "ReferenceDoseType", 1, 1, "DICOM/Supplement_175",
+      EVR_CS, "ReferenceDoseType", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x061b, 0x300a, 0x061b,
-      EVR_CS, "PrimaryDoseValueIndicator", 1, 1, "DICOM/Supplement_175",
+      EVR_CS, "PrimaryDoseValueIndicator", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x061c, 0x300a, 0x061c,
-      EVR_SQ, "DoseValuesSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "DoseValuesSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x061d, 0x300a, 0x061d,
-      EVR_CS, "DoseValuePurpose", 1, -1, "DICOM/Supplement_175",
+      EVR_CS, "DoseValuePurpose", 1, -1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x061e, 0x300a, 0x061e,
-      EVR_FD, "ReferenceDosePointCoordinates", 3, 3, "DICOM/Supplement_175",
+      EVR_FD, "ReferenceDosePointCoordinates", 3, 3, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x061f, 0x300a, 0x061f,
-      EVR_SQ, "RadiationDoseValuesParametersSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "RadiationDoseValuesParametersSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0620, 0x300a, 0x0620,
-      EVR_SQ, "MetersetToDoseMappingSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "MetersetToDoseMappingSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0621, 0x300a, 0x0621,
-      EVR_SQ, "ExpectedInVivoMeasurementValuesSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "ExpectedInVivoMeasurementValuesSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0622, 0x300a, 0x0622,
-      EVR_US, "ExpectedInVivoMeasurementValueIndex", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "ExpectedInVivoMeasurementValueIndex", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0623, 0x300a, 0x0623,
-      EVR_LO, "RadiationDoseInVivoMeasurementLabel", 1, 1, "DICOM/Supplement_175",
+      EVR_LO, "RadiationDoseInVivoMeasurementLabel", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0624, 0x300a, 0x0624,
-      EVR_FD, "RadiationDoseCentralAxisDisplacement", 2, 2, "DICOM/Supplement_175",
+      EVR_FD, "RadiationDoseCentralAxisDisplacement", 2, 2, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0625, 0x300a, 0x0625,
-      EVR_FD, "RadiationDoseValue", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "RadiationDoseValue", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0626, 0x300a, 0x0626,
-      EVR_FD, "RadiationDoseSourceToSkinDistance", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "RadiationDoseSourceToSkinDistance", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0627, 0x300a, 0x0627,
-      EVR_FD, "RadiationDoseMeasurementPointCoordinates", 3, 3, "DICOM/Supplement_175",
+      EVR_FD, "RadiationDoseMeasurementPointCoordinates", 3, 3, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0628, 0x300a, 0x0628,
-      EVR_FD, "RadiationDoseSourceToExternalContourDistance", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "RadiationDoseSourceToExternalContourDistance", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0629, 0x300a, 0x0629,
-      EVR_SQ, "RTToleranceSetSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "RTToleranceSetSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x062a, 0x300a, 0x062a,
-      EVR_LO, "RTToleranceSetLabel", 1, 1, "DICOM/Supplement_175",
+      EVR_LO, "RTToleranceSetLabel", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x062b, 0x300a, 0x062b,
-      EVR_SQ, "AttributeToleranceValuesSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "AttributeToleranceValuesSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x062c, 0x300a, 0x062c,
-      EVR_FD, "ToleranceValue", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "ToleranceValue", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x062d, 0x300a, 0x062d,
-      EVR_SQ, "PatientSupportPositionToleranceSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "PatientSupportPositionToleranceSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x062e, 0x300a, 0x062e,
-      EVR_FD, "TreatmentTimeLimit", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "TreatmentTimeLimit", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x062f, 0x300a, 0x062f,
-      EVR_SQ, "CArmPhotonElectronControlPointSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "CArmPhotonElectronControlPointSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0630, 0x300a, 0x0630,
-      EVR_SQ, "ReferencedRTRadiationSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "ReferencedRTRadiationSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0631, 0x300a, 0x0631,
-      EVR_SQ, "ReferencedRTInstanceSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "ReferencedRTInstanceSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0632, 0x300a, 0x0632,
-      EVR_SQ, "ReferencedRTPatientSetupSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "ReferencedRTPatientSetupSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0634, 0x300a, 0x0634,
-      EVR_FD, "SourceToPatientSurfaceDistance", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "SourceToPatientSurfaceDistance", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0635, 0x300a, 0x0635,
-      EVR_SQ, "TreatmentMachineSpecialModeCodeSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "TreatmentMachineSpecialModeCodeSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0636, 0x300a, 0x0636,
-      EVR_US, "IntendedNumberOfFractions", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "IntendedNumberOfFractions", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0637, 0x300a, 0x0637,
-      EVR_CS, "RTRadiationSetIntent", 1, 1, "DICOM/Supplement_175",
+      EVR_CS, "RTRadiationSetIntent", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0638, 0x300a, 0x0638,
-      EVR_CS, "RTRadiationPhysicalAndGeometricContentDetailFlag", 1, 1, "DICOM/Supplement_175",
+      EVR_CS, "RTRadiationPhysicalAndGeometricContentDetailFlag", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0639, 0x300a, 0x0639,
-      EVR_CS, "RTRecordFlag", 1, 1, "DICOM/Supplement_175",
+      EVR_CS, "RTRecordFlag", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x063a, 0x300a, 0x063a,
-      EVR_SQ, "TreatmentDeviceIdentificationSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "TreatmentDeviceIdentificationSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x063b, 0x300a, 0x063b,
-      EVR_SQ, "ReferencedRTPhysicianIntentSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "ReferencedRTPhysicianIntentSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x063c, 0x300a, 0x063c,
-      EVR_FD, "CumulativeMeterset", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "CumulativeMeterset", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x063d, 0x300a, 0x063d,
-      EVR_FD, "DeliveryRate", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "DeliveryRate", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x063e, 0x300a, 0x063e,
-      EVR_SQ, "DeliveryRateUnitSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "DeliveryRateUnitSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x063f, 0x300a, 0x063f,
-      EVR_SQ, "TreatmentPositionSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "TreatmentPositionSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0640, 0x300a, 0x0640,
-      EVR_FD, "RadiationSourceAxisDistance", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "RadiationSourceAxisDistance", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0641, 0x300a, 0x0641,
-      EVR_US, "NumberOfRTBeamLimitingDevices", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "NumberOfRTBeamLimitingDevices", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0642, 0x300a, 0x0642,
-      EVR_FD, "RTBeamLimitingDeviceProximalDistance", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "RTBeamLimitingDeviceProximalDistance", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0643, 0x300a, 0x0643,
-      EVR_FD, "RTBeamLimitingDeviceDistalDistance", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "RTBeamLimitingDeviceDistalDistance", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0644, 0x300a, 0x0644,
-      EVR_SQ, "ParallelRTBeamDelimiterDeviceOrientationLabelCodeSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "ParallelRTBeamDelimiterDeviceOrientationLabelCodeSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0645, 0x300a, 0x0645,
-      EVR_FD, "BeamsModifierOrientationAngle", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "BeamModifierOrientationAngle", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0646, 0x300a, 0x0646,
-      EVR_SQ, "FixedRTBeamDelimiterDeviceSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "FixedRTBeamDelimiterDeviceSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0647, 0x300a, 0x0647,
-      EVR_SQ, "ParallelRTBeamDelimiterDeviceSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "ParallelRTBeamDelimiterDeviceSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0648, 0x300a, 0x0648,
-      EVR_US, "NumberOfParallelRTBeamDelimiters", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "NumberOfParallelRTBeamDelimiters", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0649, 0x300a, 0x0649,
-      EVR_FD, "ParallelRTBeamDelimiterBoundaries", 2, -1, "DICOM/Supplement_175",
+      EVR_FD, "ParallelRTBeamDelimiterBoundaries", 2, -1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x064a, 0x300a, 0x064a,
-      EVR_FD, "ParallelRTBeamDelimiterPositions", 2, -1, "DICOM/Supplement_175",
+      EVR_FD, "ParallelRTBeamDelimiterPositions", 2, -1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x064b, 0x300a, 0x064b,
-      EVR_FD, "RTBeamLimitingDeviceOffset", 2, 2, "DICOM/Supplement_175",
+      EVR_FD, "RTBeamLimitingDeviceOffset", 2, 2, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x064c, 0x300a, 0x064c,
-      EVR_SQ, "RTBeamDelimiterGeometrySequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "RTBeamDelimiterGeometrySequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x064d, 0x300a, 0x064d,
-      EVR_SQ, "RTBeamLimitingDeviceDefinitionSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "RTBeamLimitingDeviceDefinitionSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x064e, 0x300a, 0x064e,
-      EVR_CS, "ParallelRTBeamDelimiterOpeningMode", 1, 1, "DICOM/Supplement_175",
+      EVR_CS, "ParallelRTBeamDelimiterOpeningMode", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x064f, 0x300a, 0x064f,
-      EVR_CS, "ParallelRTBeamDelimiterLeafMountingSide", 1, -1, "DICOM/Supplement_175",
+      EVR_CS, "ParallelRTBeamDelimiterLeafMountingSide", 1, -1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0650, 0x300a, 0x0650,
-      EVR_UI, "PatientSetupUID", 1, 1, "DICOM/Supplement_175",
+      EVR_UI, "PatientSetupUID", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0651, 0x300a, 0x0651,
-      EVR_SQ, "WedgeDefinitionSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "WedgeDefinitionSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0652, 0x300a, 0x0652,
-      EVR_FD, "RadiationBeamWedgeAngle", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "RadiationBeamWedgeAngle", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0653, 0x300a, 0x0653,
-      EVR_FD, "RadiationBeamWedgeThinEdgeDistance", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "RadiationBeamWedgeThinEdgeDistance", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0654, 0x300a, 0x0654,
-      EVR_FD, "RadiationBeamEffectiveWedgeAngle", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "RadiationBeamEffectiveWedgeAngle", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0655, 0x300a, 0x0655,
-      EVR_US, "NumberOfWedgePositions", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "NumberOfWedgePositions", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0656, 0x300a, 0x0656,
-      EVR_SQ, "RTBeamLimitingDeviceOpeningSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "RTBeamLimitingDeviceOpeningSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0657, 0x300a, 0x0657,
-      EVR_US, "NumberOfRTBeamLimitingDeviceOpenings", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "NumberOfRTBeamLimitingDeviceOpenings", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0658, 0x300a, 0x0658,
-      EVR_SQ, "RadiationDosimeterUnitSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "RadiationDosimeterUnitSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0659, 0x300a, 0x0659,
-      EVR_SQ, "RTDeviceDistanceReferenceLocationCodeSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "RTDeviceDistanceReferenceLocationCodeSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x065a, 0x300a, 0x065a,
-      EVR_SQ, "RadiationDeviceConfigurationAndCommissioningKeySequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "RadiationDeviceConfigurationAndCommissioningKeySequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x065b, 0x300a, 0x065b,
-      EVR_SQ, "PatientSupportPositionParameterSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "PatientSupportPositionParameterSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x065c, 0x300a, 0x065c,
-      EVR_CS, "PatientSupportPositionSpecificationMethod", 1, 1, "DICOM/Supplement_175",
+      EVR_CS, "PatientSupportPositionSpecificationMethod", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x065d, 0x300a, 0x065d,
-      EVR_SQ, "PatientSupportPositionDeviceParameterSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "PatientSupportPositionDeviceParameterSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x065e, 0x300a, 0x065e,
-      EVR_US, "DeviceOrderIndex", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "DeviceOrderIndex", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x065f, 0x300a, 0x065f,
-      EVR_US, "PatientSupportPositionParameterOrderIndex", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "PatientSupportPositionParameterOrderIndex", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0660, 0x300a, 0x0660,
-      EVR_SQ, "PatientSupportPositionDeviceToleranceSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "PatientSupportPositionDeviceToleranceSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0661, 0x300a, 0x0661,
-      EVR_US, "PatientSupportPositionToleranceOrderIndex", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "PatientSupportPositionToleranceOrderIndex", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0662, 0x300a, 0x0662,
-      EVR_SQ, "CompensatorDefinitionSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "CompensatorDefinitionSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0663, 0x300a, 0x0663,
-      EVR_CS, "CompensatorMapOrientation", 1, 1, "DICOM/Supplement_175",
+      EVR_CS, "CompensatorMapOrientation", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0664, 0x300a, 0x0664,
-      EVR_OF, "CompensatorProximalThicknessMap", 1, 1, "DICOM/Supplement_175",
+      EVR_OF, "CompensatorProximalThicknessMap", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0665, 0x300a, 0x0665,
-      EVR_OF, "CompensatorDistalThicknessMap", 1, 1, "DICOM/Supplement_175",
+      EVR_OF, "CompensatorDistalThicknessMap", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0666, 0x300a, 0x0666,
-      EVR_FD, "CompensatorBasePlaneOffset", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "CompensatorBasePlaneOffset", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0667, 0x300a, 0x0667,
-      EVR_SQ, "CompensatorShapeFabricationCodeSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "CompensatorShapeFabricationCodeSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0668, 0x300a, 0x0668,
-      EVR_SQ, "CompensatorShapeSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "CompensatorShapeSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0669, 0x300a, 0x0669,
-      EVR_FD, "RadiationBeamCompensatorMillingToolDiameter", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "RadiationBeamCompensatorMillingToolDiameter", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x066a, 0x300a, 0x066a,
-      EVR_SQ, "BlockDefinitionSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "BlockDefinitionSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x066b, 0x300a, 0x066b,
-      EVR_OF, "BlockEdgeData", 1, 1, "DICOM/Supplement_175",
+      EVR_OF, "BlockEdgeData", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x066c, 0x300a, 0x066c,
-      EVR_CS, "BlockOrientation", 1, 1, "DICOM/Supplement_175",
+      EVR_CS, "BlockOrientation", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x066d, 0x300a, 0x066d,
-      EVR_FD, "RadiationBeamBlockThickness", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "RadiationBeamBlockThickness", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x066e, 0x300a, 0x066e,
-      EVR_FD, "RadiationBeamBlockSlabThickness", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "RadiationBeamBlockSlabThickness", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x066f, 0x300a, 0x066f,
-      EVR_SQ, "BlockEdgeDataSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "BlockEdgeDataSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0670, 0x300a, 0x0670,
-      EVR_US, "NumberOfRTAccessoryHolders", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "NumberOfRTAccessoryHolders", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0671, 0x300a, 0x0671,
-      EVR_SQ, "GeneralAccessoryDefinitionSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "GeneralAccessoryDefinitionSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0672, 0x300a, 0x0672,
-      EVR_US, "NumberOfGeneralAccessories", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "NumberOfGeneralAccessories", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0673, 0x300a, 0x0673,
-      EVR_SQ, "BolusDefinitionSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "BolusDefinitionSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0674, 0x300a, 0x0674,
-      EVR_US, "NumberOfBoluses", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "NumberOfBoluses", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0675, 0x300a, 0x0675,
-      EVR_UI, "EquipmentFrameOfReferenceUID", 1, 1, "DICOM/Supplement_175",
+      EVR_UI, "EquipmentFrameOfReferenceUID", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0676, 0x300a, 0x0676,
-      EVR_ST, "EquipmentFrameOfReferenceDescription", 1, 1, "DICOM/Supplement_175",
+      EVR_ST, "EquipmentFrameOfReferenceDescription", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0677, 0x300a, 0x0677,
-      EVR_SQ, "EquipmentReferencePointCoordinatesSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "EquipmentReferencePointCoordinatesSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0678, 0x300a, 0x0678,
-      EVR_SQ, "EquipmentReferencePointCodeSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "EquipmentReferencePointCodeSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0679, 0x300a, 0x0679,
-      EVR_FD, "RTBeamLimitingDeviceAngle", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "RTBeamLimitingDeviceAngle", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x067a, 0x300a, 0x067a,
-      EVR_FD, "SourceRollAngle", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "SourceRollAngle", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x067b, 0x300a, 0x067b,
-      EVR_SQ, "RadiationGenerationModeSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "RadiationGenerationModeSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x067c, 0x300a, 0x067c,
-      EVR_SH, "RadiationGenerationModeLabel", 1, 1, "DICOM/Supplement_175",
+      EVR_SH, "RadiationGenerationModeLabel", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x067d, 0x300a, 0x067d,
-      EVR_ST, "RadiationGenerationModeDescription", 1, 1, "DICOM/Supplement_175",
+      EVR_ST, "RadiationGenerationModeDescription", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x067e, 0x300a, 0x067e,
-      EVR_SQ, "RadiationGenerationModeMachineCodeSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "RadiationGenerationModeMachineCodeSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x067f, 0x300a, 0x067f,
-      EVR_SQ, "RadiationTypeCodeSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "RadiationTypeCodeSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0680, 0x300a, 0x0680,
-      EVR_DS, "NominalEnergy", 1, 1, "DICOM/Supplement_175",
+      EVR_DS, "NominalEnergy", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0681, 0x300a, 0x0681,
-      EVR_DS, "MinimumNominalEnergy", 1, 1, "DICOM/Supplement_175",
+      EVR_DS, "MinimumNominalEnergy", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0682, 0x300a, 0x0682,
-      EVR_DS, "MaximumNominalEnergy", 1, 1, "DICOM/Supplement_175",
+      EVR_DS, "MaximumNominalEnergy", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0683, 0x300a, 0x0683,
-      EVR_SQ, "RadiationFluenceModifierCodeSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "RadiationFluenceModifierCodeSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0684, 0x300a, 0x0684,
-      EVR_SQ, "EnergyUnitCodeSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "EnergyUnitCodeSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0685, 0x300a, 0x0685,
-      EVR_US, "NumberOfRadiationGenerationModes", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "NumberOfRadiationGenerationModes", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0686, 0x300a, 0x0686,
-      EVR_SQ, "PatientSupportDevicesSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "PatientSupportDevicesSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0687, 0x300a, 0x0687,
-      EVR_US, "NumberOfPatientSupportDevices", 1, 1, "DICOM/Supplement_175",
+      EVR_US, "NumberOfPatientSupportDevices", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0688, 0x300a, 0x0688,
-      EVR_FD, "RTBeamModifierDefinitionDistance", 1, 1, "DICOM/Supplement_175",
+      EVR_FD, "RTBeamModifierDefinitionDistance", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300a, 0x0689, 0x300a, 0x0689,
-      EVR_SQ, "BeamAreaLimitSequence", 1, 1, "DICOM/Supplement_175",
+      EVR_SQ, "BeamAreaLimitSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x068a, 0x300a, 0x068a,
+      EVR_SQ, "ReferencedRTPrescriptionSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0700, 0x300a, 0x0700,
+      EVR_UI, "TreatmentSessionUID", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0701, 0x300a, 0x0701,
+      EVR_CS, "RTRadiationUsage", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0702, 0x300a, 0x0702,
+      EVR_SQ, "ReferencedRTRadiationSetSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0703, 0x300a, 0x0703,
+      EVR_SQ, "ReferencedRTRadiationRecordSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0704, 0x300a, 0x0704,
+      EVR_US, "RTRadiationSetDeliveryNumber", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0705, 0x300a, 0x0705,
+      EVR_US, "ClinicalFractionNumber", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0706, 0x300a, 0x0706,
+      EVR_CS, "RTTreatmentFractionCompletionStatus", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0707, 0x300a, 0x0707,
+      EVR_CS, "RTRadiationSetUsage", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0708, 0x300a, 0x0708,
+      EVR_CS, "TreatmentDeliveryContinuationFlag", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0709, 0x300a, 0x0709,
+      EVR_CS, "TreatmentRecordContentOrigin", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0714, 0x300a, 0x0714,
+      EVR_CS, "RTTreatmentTerminationStatus", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0715, 0x300a, 0x0715,
+      EVR_SQ, "RTTreatmentTerminationReasonCodeSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0716, 0x300a, 0x0716,
+      EVR_SQ, "MachineSpecificTreatmentTerminationCodeSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0722, 0x300a, 0x0722,
+      EVR_SQ, "RTRadiationSalvageRecordControlPointSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0723, 0x300a, 0x0723,
+      EVR_CS, "StartingMetersetValueKnownFlag", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0730, 0x300a, 0x0730,
+      EVR_ST, "TreatmentTerminationDescription", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0731, 0x300a, 0x0731,
+      EVR_SQ, "TreatmentToleranceViolationSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0732, 0x300a, 0x0732,
+      EVR_CS, "TreatmentToleranceViolationCategory", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0733, 0x300a, 0x0733,
+      EVR_SQ, "TreatmentToleranceViolationAttributeSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0734, 0x300a, 0x0734,
+      EVR_ST, "TreatmentToleranceViolationDescription", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0735, 0x300a, 0x0735,
+      EVR_ST, "TreatmentToleranceViolationIdentification", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0736, 0x300a, 0x0736,
+      EVR_DT, "TreatmentToleranceViolationDateTime", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x073a, 0x300a, 0x073a,
+      EVR_DT, "RecordedRTControlPointDateTime", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x073b, 0x300a, 0x073b,
+      EVR_US, "ReferencedRadiationRTControlPointIndex", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x073e, 0x300a, 0x073e,
+      EVR_SQ, "AlternateValueSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x073f, 0x300a, 0x073f,
+      EVR_SQ, "ConfirmationSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0740, 0x300a, 0x0740,
+      EVR_SQ, "InterlockSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0741, 0x300a, 0x0741,
+      EVR_DT, "InterlockDateTime", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0742, 0x300a, 0x0742,
+      EVR_ST, "InterlockDescription", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0743, 0x300a, 0x0743,
+      EVR_SQ, "InterlockOriginatingDeviceSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0744, 0x300a, 0x0744,
+      EVR_SQ, "InterlockCodeSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0745, 0x300a, 0x0745,
+      EVR_SQ, "InterlockResolutionCodeSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0746, 0x300a, 0x0746,
+      EVR_SQ, "InterlockResolutionUserSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0760, 0x300a, 0x0760,
+      EVR_DT, "OverrideDateTime", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0761, 0x300a, 0x0761,
+      EVR_SQ, "TreatmentToleranceViolationTypeCodeSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0762, 0x300a, 0x0762,
+      EVR_SQ, "TreatmentToleranceViolationCauseCodeSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0772, 0x300a, 0x0772,
+      EVR_SQ, "MeasuredMetersetToDoseMappingSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0773, 0x300a, 0x0773,
+      EVR_US, "ReferencedExpectedInVivoMeasurementValueIndex", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0774, 0x300a, 0x0774,
+      EVR_SQ, "DoseMeasurementDeviceCodeSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0780, 0x300a, 0x0780,
+      EVR_SQ, "AdditionalParameterRecordingInstanceSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x300a, 0x0783, 0x300a, 0x0783,
+      EVR_ST, "InterlockOriginDescription", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x300c, 0x0002, 0x300c, 0x0002,
@@ -29066,6 +29444,10 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       EVR_SQ, "DeviceTypeCodeSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
+  , { 0x3010, 0x002f, 0x3010, 0x002f,
+      EVR_SQ, "SegmentAnnotationTypeModifierCodeSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
   , { 0x3010, 0x0030, 0x3010, 0x0030,
       EVR_SQ, "PatientEquipmentRelationshipCodeSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
@@ -29418,6 +29800,54 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       EVR_SQ, "DeliveryTimeStructureCodeSequence", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
+  , { 0x3010, 0x0089, 0x3010, 0x0089,
+      EVR_SQ, "TreatmentSiteModifierCodeSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x3010, 0x0090, 0x3010, 0x0090,
+      EVR_CS, "RoboticBaseLocationIndicator", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x3010, 0x0091, 0x3010, 0x0091,
+      EVR_SQ, "RoboticPathNodeSetCodeSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x3010, 0x0092, 0x3010, 0x0092,
+      EVR_UL, "RoboticNodeIdentifier", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x3010, 0x0093, 0x3010, 0x0093,
+      EVR_FD, "RTTreatmentSourceCoordinates", 3, 3, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x3010, 0x0094, 0x3010, 0x0094,
+      EVR_FD, "RadiationSourceCoordinateSystemYawAngle", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x3010, 0x0095, 0x3010, 0x0095,
+      EVR_FD, "RadiationSourceCoordinateSystemRollAngle", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x3010, 0x0096, 0x3010, 0x0096,
+      EVR_FD, "RadiationSourceCoordinateSystemPitchAngle", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x3010, 0x0097, 0x3010, 0x0097,
+      EVR_SQ, "RoboticPathControlPointSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x3010, 0x0098, 0x3010, 0x0098,
+      EVR_SQ, "TomotherapeuticControlPointSequence", 1, 1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x3010, 0x0099, 0x3010, 0x0099,
+      EVR_FD, "TomotherapeuticLeafOpenDurations", 1, -1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
+  , { 0x3010, 0x009a, 0x3010, 0x009a,
+      EVR_FD, "TomotherapeuticLeafInitialClosedDurations", 1, -1, "DICOM",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      NULL }
 #ifdef ENABLE_PRIVATE_TAGS
   , { 0x3f01, 0x0001, 0x3f01, 0x0001,
       EVR_LO, "InstitutionCode", 1, 1, "PrivateTag",
@@ -29743,7 +30173,7 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x4010, 0x1029, 0x4010, 0x1029,
-      EVR_LO, "ThreatDetectionAlgorithmandVersion", 1, -1, "DICOM/DICOS",
+      EVR_LO, "ThreatDetectionAlgorithmAndVersion", 1, -1, "DICOM/DICOS",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x4010, 0x102a, 0x4010, 0x102a,
@@ -30079,7 +30509,7 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x7fe0, 0x0010, 0x7fe0, 0x0010,
-      EVR_ox, "PixelData", 1, 1, "DICOM",
+      EVR_px, "PixelData", 1, 1, "DICOM",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       NULL }
   , { 0x7fe0, 0x0020, 0x7fe0, 0x0020,
@@ -30107,6 +30537,10 @@ static const DBI_SimpleEntry simpleBuiltinDict[] = {
       EVR_ox, "PixelData", 1, 1, "PrivateTag",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
       "SPI-P Release 1" }
+  , { 0x7fe1, 0x1060, 0x7fe1, 0x1060,
+      EVR_px, "IllegalPrivatePixelSequence", 1, 1, "PrivateTag",
+      DcmDictRange_Unspecified, DcmDictRange_Unspecified,
+      "GEMS_Ultrasound_MovieGroup_001" }
   , { 0x7fe3, 0x0000, 0x7fe3, 0x0000,
       EVR_LT, "ImageGraphicsFormatCode", 1, 1, "PrivateTag",
       DcmDictRange_Unspecified, DcmDictRange_Unspecified,
index 12dcf4c9b1b37f8a9bb492691146d9da79d985f4..86f6f4442f90d2ff4ce76096af388fbe26e7141e 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -1176,7 +1176,7 @@ OFCondition DcmElement::read(DcmInputStream &inStream,
             {
                 /* Return error code if we are are not ignoring parsing errors */
                 if (!dcmIgnoreParsingErrors.get())
-                    errorFlag = EC_StreamNotifyClient;
+                    errorFlag = EC_StreamNotifyClient; // should we rather return EC_InvalidStream?
                 /* In any case, make sure that calling the load value routine on this
                  * element will fail later. For that, create the stream factory that
                  * the load routine will use. Otherwise it would not realize
@@ -1304,15 +1304,15 @@ OFCondition DcmElement::write(DcmOutputStream &outStream,
 
     if ((elemLength) > 0xffff && (! myvalidvr.usesExtendedLengthEncoding()) && outXfer.isExplicitVR())
     {
-      /* special case: we are writing in explicit VR, the VR of this
-       * element uses a 2-byte length encoding, but the element length is
-       * too large for a 2-byte length field. We need to write this element
-       * as VR=UN (or VR=OB if the generation of UN is disabled).
-       * In this method, the variable "vr" is only used to determine the
-       * output byte order, which is always the same for OB and UN.
-       * Therefore, we do not need to distinguish between these two.
-       */
-       vr = EVR_UN;
+        /* special case: we are writing in explicit VR, the VR of this
+         * element uses a 2-byte length encoding, but the element length is
+         * too large for a 2-byte length field. We need to write this element
+         * as VR=UN (or VR=OB if the generation of UN is disabled).
+         * In this method, the variable "vr" is only used to determine the
+         * output byte order, which is always the same for OB and UN.
+         * Therefore, we do not need to distinguish between these two.
+         */
+        vr = EVR_UN;
     }
 
     /* In case the transfer state is not initialized, this is an illegal call */
@@ -1661,7 +1661,7 @@ void DcmElement::writeJsonOpener(STD_NAMESPACE ostream &out,
     /* write attribute tag */
     out << ++format.indent() << "\""
         << STD_NAMESPACE hex << STD_NAMESPACE setfill('0')
-        << STD_NAMESPACE setw(4) << tag.getGTag();
+        << STD_NAMESPACE setw(4) << STD_NAMESPACE uppercase << tag.getGTag();
     /* write "ggggeeee" (no comma, upper case!) */
     /* for private element numbers, zero out 2 first element digits */
     /* or output full element number "eeee" */
index d83430dcd97708d33626559c57cf9afc2a3d8fa4..f4655eaafc09e11ed8c545c53e9838a4b33e7b06 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2018-2019, OFFIS e.V.
+ *  Copyright (C) 2018-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -13,7 +13,7 @@
  *
  *  Module:  dcmdata
  *
- *  Author:  Pedro Arizpe
+ *  Author:  Pedro ArizpeGomez
  *
  *  Purpose: Implementation of Document encapsulation
  *
 #define EXITCODE_MEMORY_EXHAUSTED                4
 
 DcmEncapsulatedDocument::DcmEncapsulatedDocument() :
-  opt_patientBirthdate(),
-  opt_patientID(),
-  opt_patientName(),
-  opt_patientSex(),
+        opt_patientBirthdate(),
+        opt_patientID(),
+        opt_patientName(),
+        opt_patientSex(),
 
-  opt_conceptCM(),
-  opt_conceptCSD(),
-  opt_conceptCV(),
+        opt_conceptCM(),
+        opt_conceptCSD(),
+        opt_conceptCV(),
 
-  opt_documentTitle(),
-  opt_seriesFile(),
-  opt_seriesUID(),
-  opt_studyUID(),
+        opt_documentTitle(),
+        opt_seriesFile(),
+        opt_seriesUID(),
+        opt_studyUID(),
 
-  opt_oenctype(EET_ExplicitLength),
-  opt_writeMode(EWM_fileformat),
-  opt_oglenc(EGL_withoutGL),
-  opt_opadenc(EPD_withoutPadding),
-  opt_oxfer(EXS_LittleEndianExplicit),
-  opt_filepad(0),
-  opt_itempad(0),
+        opt_oenctype(EET_ExplicitLength),
+        opt_writeMode(EWM_fileformat),
+        opt_oglenc(EGL_withoutGL),
+        opt_opadenc(EPD_withoutPadding),
+        opt_oxfer(EXS_LittleEndianExplicit),
+        opt_filepad(0),
+        opt_itempad(0),
 
-  opt_readSeriesInfo(OFFalse),
-  opt_annotation(OFTrue),
-  opt_increment(OFFalse),
+        opt_readSeriesInfo(OFFalse),
+        opt_annotation(OFTrue),
+        opt_increment(OFFalse),
 
-  opt_instance(1),
-  opt_overrideKeys(),
+        opt_instance(1),
+        opt_overrideKeys(),
 
-  cda_mediaTypes(),
-  hl7_InstanceIdentifier(),
-  opt_override(OFFalse),
-  // Frame of Reference Module (STL)
-  opt_frameOfReferenceUID(),
-  opt_positionReferenceIndicator(),
-  // Frame of Reference Module (STL)
-  opt_manufacturer(),
-  opt_manufacturerModelName(),
-  opt_deviceSerialNumber(),
-  opt_softwareVersions(),
-  // Enhanced General Equipment Module (STL)
-  opt_measurementUnitsCM(),
-  opt_measurementUnitsCSD(),
-  opt_measurementUnitsCV(),
-  //encapsulation file type
-  ftype()
+        cda_mediaTypes(),
+        hl7_InstanceIdentifier(),
+        opt_override(OFFalse),
+        // Frame of Reference Module (STL)
+        opt_frameOfReferenceUID(),
+        opt_positionReferenceIndicator(),
+        // Frame of Reference Module (STL)
+        opt_manufacturer(),
+        opt_manufacturerModelName(),
+        opt_deviceSerialNumber(),
+        opt_softwareVersions(),
+        // Enhanced General Equipment Module (STL)
+        opt_measurementUnitsCM(),
+        opt_measurementUnitsCSD(),
+        opt_measurementUnitsCV(),
+        //encapsulation file type
+        ftype()
 {
 }
 
 OFBool DcmEncapsulatedDocument::XMLsearchAttribute(
-  XMLNode currnode,
-  OFList<OFString> *results,
-  OFString attr)
+        XMLNode currnode,
+        OFList<OFString> *results,
+        OFString attr)
 {
   OFBool found = OFFalse;
 #ifndef _XMLWIDECHAR
@@ -133,8 +133,8 @@ OFBool DcmEncapsulatedDocument::XMLsearchAttribute(
 }
 
 OFString DcmEncapsulatedDocument::XMLgetAllAttributeValues(
-  XMLNode fileNode,
-  OFString attr)
+        XMLNode fileNode,
+        OFString attr)
 {
   OFString attributeValues;
 #ifndef _XMLWIDECHAR
@@ -168,8 +168,8 @@ OFString DcmEncapsulatedDocument::XMLgetAllAttributeValues(
 }
 
 OFString DcmEncapsulatedDocument::XMLgetAttribute(
-  XMLNode fileNode,
-  DcmTagKey attr)
+        XMLNode fileNode,
+        DcmTagKey attr)
 {
   OFString result = "";
 #ifndef _XMLWIDECHAR
@@ -182,9 +182,8 @@ OFString DcmEncapsulatedDocument::XMLgetAttribute(
   }
   if (attr == DCM_HL7InstanceIdentifier)
   {
-      result = OFString(OFSTRING_GUARD(
-        fileNode.getChildNode("id").getAttribute("root"))) + "^" + OFString(OFSTRING_GUARD(
-          fileNode.getChildNode("id").getAttribute("extension")));
+    result = OFString(OFSTRING_GUARD(fileNode.getChildNode("id").getAttribute("root"))) + "^"
+             + OFString(OFSTRING_GUARD(fileNode.getChildNode("id").getAttribute("extension")));
   }
   /*PatientNameExtension could reflect the type of name (PHON, IDE, ABC)
   if (attr == DCM_PatientNameExtension)
@@ -193,25 +192,35 @@ OFString DcmEncapsulatedDocument::XMLgetAttribute(
   }*/
   if (attr == DCM_PatientName)
   {
-    result = OFString(OFSTRING_GUARD(
-      fileNode.getChildNodeByPath("recordTarget/patientRole/patient/name/family").getText())) + "^" + OFString(OFSTRING_GUARD(
-        fileNode.getChildNodeByPath("recordTarget/patientRole/patient/name").getChildNode("given", 0).getText())) + "^" + OFString(OFSTRING_GUARD(
-          fileNode.getChildNodeByPath("recordTarget/patientRole/patient/name").getChildNode("given", 1).getText())) + "^" + OFString(OFSTRING_GUARD(
-            fileNode.getChildNodeByPath("recordTarget/patientRole/patient/name/prefix").getText())) + "^" + OFString(OFSTRING_GUARD(
-              fileNode.getChildNodeByPath("recordTarget/patientRole/patient/name/suffix").getText()));
+    result = OFString(
+            OFSTRING_GUARD(fileNode.getChildNodeByPath("recordTarget/patientRole/patient/name/family").getText())) + "^"
+             + OFString(OFSTRING_GUARD(
+                                fileNode.getChildNodeByPath("recordTarget/patientRole/patient/name").getChildNode(
+                                        "given", 0).getText())) + "^"
+             + OFString(OFSTRING_GUARD(
+                                fileNode.getChildNodeByPath("recordTarget/patientRole/patient/name").getChildNode(
+                                        "given", 1).getText())) + "^"
+             + OFString(
+            OFSTRING_GUARD(fileNode.getChildNodeByPath("recordTarget/patientRole/patient/name/prefix").getText())) + "^"
+             + OFString(
+            OFSTRING_GUARD(fileNode.getChildNodeByPath("recordTarget/patientRole/patient/name/suffix").getText()));
   }
   if (attr == DCM_PatientSex)
   {
-    result = OFString(OFSTRING_GUARD(fileNode.getChildNodeByPath("recordTarget/patientRole/patient/administrativeGenderCode").getAttribute("code")));
+    result = OFString(OFSTRING_GUARD(fileNode.getChildNodeByPath(
+            "recordTarget/patientRole/patient/administrativeGenderCode").getAttribute("code")));
   }
   if (attr == DCM_PatientBirthDate)
   {
-    result = OFString(OFSTRING_GUARD(fileNode.getChildNodeByPath("recordTarget/patientRole/patient/birthTime").getAttribute("value")));
+    result = OFString(OFSTRING_GUARD(
+                              fileNode.getChildNodeByPath("recordTarget/patientRole/patient/birthTime").getAttribute(
+                                      "value")));
   }
   //Table A.8-1. Basic Code Attributes Mapping to HL7 V3 Code Data Types (CV, CS, CE and CD)
   if (attr == DCM_PatientID)
   {
-    result = OFString(OFSTRING_GUARD(fileNode.getChildNodeByPath("recordTarget/patientRole/id").getAttribute("extension")));
+    result = OFString(
+            OFSTRING_GUARD(fileNode.getChildNodeByPath("recordTarget/patientRole/id").getAttribute("extension")));
   }
   if (attr == DCM_CodeValue)//Code Value
   {
@@ -223,27 +232,27 @@ OFString DcmEncapsulatedDocument::XMLgetAttribute(
   }
   if (attr == DCM_CodingSchemeDesignator)//Coding Scheme Designator (0008,0102)
   {
-    OFString CSDtemp=OFString(OFSTRING_GUARD(fileNode.getChildNode("code").getAttribute("codeSystemName")));
+    OFString CSDtemp = OFString(OFSTRING_GUARD(fileNode.getChildNode("code").getAttribute("codeSystemName")));
     // Abbreviate most common CSNs
-    if(CSDtemp==OFString("LOINC"))
+    if (CSDtemp == OFString("LOINC"))
     {
-    result = OFString("LN");
+      result = OFString("LN");
     }
     else
     {
-      if(CSDtemp==OFString("DICOM"))
+      if (CSDtemp == OFString("DICOM"))
       {
-      result = OFString("DC");
+        result = OFString("DC");
       }
       else
       {
-        if(CSDtemp==OFString("SNOMED"))
+        if (CSDtemp == OFString("SNOMED"))
         {
           result = OFString("SRT");
         }
         else
         {
-          result=CSDtemp;
+          result = CSDtemp;
         }
       }
     }
@@ -261,10 +270,11 @@ OFString DcmEncapsulatedDocument::XMLgetAttribute(
 }
 
 int DcmEncapsulatedDocument::getCDAData(
-  const char *filename,
-  OFLogger &appLogger)
+        const char *filename,
+        OFLogger &appLogger)
 {
 #ifdef _XMLWIDECHAR
+#warning "DCMTK compiled with 'wide char XML parser'. cda2dcm will be unable to read and encapsulate CDA documents."
   OFLOG_ERROR(appLogger, "DCMTK compiled with \"wide char XML parser\". Cannot parse CDA data because of incompatible API.");
   return 99;
 #else
@@ -299,16 +309,16 @@ int DcmEncapsulatedDocument::getCDAData(
       if (!opt_override)
       {
         OFLOG_ERROR(appLogger, "Patient ID mismatch:" << OFendl
-          << "Found in the CDA file : " << pID << OFendl
-          << "Entered (or found in DCM file): " << opt_patientID << OFendl
-          << "If you wish to override, run again with +ov");
+                << "Found in the CDA file : " << pID << OFendl
+                << "Entered (or found in DCM file): " << opt_patientID << OFendl
+                << "If you wish to override, run again with +ov");
         return EXITCODE_COMMANDLINE_SYNTAX_ERROR;
       }
       else
       {
         OFLOG_WARN(appLogger, "Patient ID mismatch:" << OFendl
-          << "Found in the CDA file : " << pID << OFendl
-          << "Provided (in DCM file): " << opt_patientID);
+                << "Found in the CDA file : " << pID << OFendl
+                << "Provided (in DCM file): " << opt_patientID);
       }
     }
     else
@@ -324,15 +334,16 @@ int DcmEncapsulatedDocument::getCDAData(
       if (!opt_override)
       {
         OFLOG_ERROR(appLogger, "Patient Birth Date mismatch:" << OFendl
-          << "Found in the CDA file : " << pBirthDate << OFendl
-          << "Provided (in DCM file): " << opt_patientBirthdate << OFendl
-          << "If you wish to override, run again with +ov");
+                << "Found in the CDA file : " << pBirthDate << OFendl
+                << "Provided (in DCM file): " << opt_patientBirthdate << OFendl
+                << "If you wish to override, run again with +ov");
         return EXITCODE_COMMANDLINE_SYNTAX_ERROR;
       }
-      else {
+      else
+      {
         OFLOG_WARN(appLogger, "Patient Birth Date mismatch:" << OFendl
-          << "Found in the CDA file : " << pBirthDate << OFendl
-          << "Provided (in DCM file): " << opt_patientBirthdate);
+                << "Found in the CDA file : " << pBirthDate << OFendl
+                << "Provided (in DCM file): " << opt_patientBirthdate);
       }
     }
     else opt_patientBirthdate = pBirthDate;
@@ -345,15 +356,16 @@ int DcmEncapsulatedDocument::getCDAData(
       if (!opt_override)
       {
         OFLOG_ERROR(appLogger, "Patient Sex mismatch:" << OFendl
-          << "Found in the CDA file : " << pSex << OFendl
-          << "Provided (in DCM file): " << opt_patientSex << OFendl
-          << "If you wish to override, run again with +ov");
+                << "Found in the CDA file : " << pSex << OFendl
+                << "Provided (in DCM file): " << opt_patientSex << OFendl
+                << "If you wish to override, run again with +ov");
         return EXITCODE_COMMANDLINE_SYNTAX_ERROR;
       }
-      else {
+      else
+      {
         OFLOG_WARN(appLogger, "Patient Sex mismatch:" << OFendl
-          << "Found in the CDA file : " << pSex << OFendl
-          << "Provided (in DCM file): " << opt_patientSex);
+                << "Found in the CDA file : " << pSex << OFendl
+                << "Provided (in DCM file): " << opt_patientSex);
       }
     }
     else opt_patientSex = pSex;
@@ -366,15 +378,16 @@ int DcmEncapsulatedDocument::getCDAData(
       if (!opt_override)
       {
         OFLOG_ERROR(appLogger, "Patient Name mismatch:" << OFendl
-          << "Found in the CDA file : " << pName << OFendl
-          << "Provided (in DCM file): " << opt_patientName << OFendl
-          << "If you wish to override, run again with +ov");
+                << "Found in the CDA file : " << pName << OFendl
+                << "Provided (in DCM file): " << opt_patientName << OFendl
+                << "If you wish to override, run again with +ov");
         return EXITCODE_COMMANDLINE_SYNTAX_ERROR;
       }
-      else {
+      else
+      {
         OFLOG_WARN(appLogger, "Patient Name mismatch:" << OFendl
-          << "Found in the CDA file : " << pName << OFendl
-          << "Provided (in DCM file): " << opt_patientName);
+                << "Found in the CDA file : " << pName << OFendl
+                << "Provided (in DCM file): " << opt_patientName);
       }
     }
     else opt_patientName = pName;
@@ -395,15 +408,16 @@ int DcmEncapsulatedDocument::getCDAData(
       if (!opt_override)
       {
         OFLOG_ERROR(appLogger, "Document Title mismatch:" << OFendl
-          << "Found in the CDA file : " << dTitle << OFendl
-          << "Provided (in DCM file): " << opt_documentTitle << OFendl
-          << "If you wish to override, run again with +ov");
+                << "Found in the CDA file : " << dTitle << OFendl
+                << "Provided (in DCM file): " << opt_documentTitle << OFendl
+                << "If you wish to override, run again with +ov");
         return EXITCODE_COMMANDLINE_SYNTAX_ERROR;
       }
-      else {
+      else
+      {
         OFLOG_WARN(appLogger, "Document Title mismatch:" << OFendl
-          << "Found in the CDA file : " << dTitle << OFendl
-          << "Provided (in DCM file): " << opt_documentTitle);
+                << "Found in the CDA file : " << dTitle << OFendl
+                << "Provided (in DCM file): " << opt_documentTitle);
       }
     }
     else opt_documentTitle = dTitle;
@@ -417,15 +431,16 @@ int DcmEncapsulatedDocument::getCDAData(
       if (!opt_override)
       {
         OFLOG_ERROR(appLogger, "concept CSD mismatch:" << OFendl
-          << "Found in the CDA file : " << cCSD << OFendl
-          << "Provided (in DCM file): " << opt_conceptCSD << OFendl
-          << "If you wish to override, run again with +ov");
+                << "Found in the CDA file : " << cCSD << OFendl
+                << "Provided (in DCM file): " << opt_conceptCSD << OFendl
+                << "If you wish to override, run again with +ov");
         return EXITCODE_COMMANDLINE_SYNTAX_ERROR;
       }
-      else {
+      else
+      {
         OFLOG_WARN(appLogger, "concept CSD mismatch:" << OFendl
-          << "Found in the CDA file : " << cCSD << OFendl
-          << "Provided (in DCM file): " << opt_conceptCSD);
+                << "Found in the CDA file : " << cCSD << OFendl
+                << "Provided (in DCM file): " << opt_conceptCSD);
       }
     }
     else opt_conceptCSD = cCSD;
@@ -438,15 +453,16 @@ int DcmEncapsulatedDocument::getCDAData(
       if (!opt_override)
       {
         OFLOG_ERROR(appLogger, "concept CV mismatch:" << OFendl
-          << "Found in the CDA file : " << cCV << OFendl
-          << "Provided (in DCM file): " << opt_conceptCV << OFendl
-          << "If you wish to override, run again with +ov");
+                << "Found in the CDA file : " << cCV << OFendl
+                << "Provided (in DCM file): " << opt_conceptCV << OFendl
+                << "If you wish to override, run again with +ov");
         return EXITCODE_COMMANDLINE_SYNTAX_ERROR;
       }
-      else {
+      else
+      {
         OFLOG_WARN(appLogger, "concept CV mismatch:" << OFendl
-          << "Found in the CDA file : " << cCV << OFendl
-          << "Provided (in DCM file): " << opt_conceptCV);
+                << "Found in the CDA file : " << cCV << OFendl
+                << "Provided (in DCM file): " << opt_conceptCV);
       }
     }
     else opt_conceptCV = cCV;
@@ -459,15 +475,16 @@ int DcmEncapsulatedDocument::getCDAData(
       if (!opt_override)
       {
         OFLOG_ERROR(appLogger, "concept CM mismatch:" << OFendl
-          << "Found in the CDA file : " << cCM << OFendl
-          << "Provided (in DCM file): " << opt_conceptCM << OFendl
-          << "If you wish to override, run again with +ov");
+                << "Found in the CDA file : " << cCM << OFendl
+                << "Provided (in DCM file): " << opt_conceptCM << OFendl
+                << "If you wish to override, run again with +ov");
         return EXITCODE_COMMANDLINE_SYNTAX_ERROR;
       }
-      else {
+      else
+      {
         OFLOG_WARN(appLogger, "concept CM mismatch:" << OFendl
-          << "Found in the CDA file : " << cCM << OFendl
-          << "Provided (in DCM file): " << opt_conceptCM);
+                << "Found in the CDA file : " << cCM << OFendl
+                << "Provided (in DCM file): " << opt_conceptCM);
       }
     }
     else opt_conceptCM = cCM;
@@ -481,13 +498,15 @@ void DcmEncapsulatedDocument::addCDACommandlineOptions(OFCommandLine &cmd)
   ftype = "cda";
   cmd.setOptionColumns(LONGCOL, SHORTCOL);
   cmd.setParamColumn(LONGCOL + SHORTCOL + 4);
-  cmd.addParam(     "cdafile-in",                         "CDA input filename to be converted");
-  cmd.addParam(     "dcmfile-out",                        "DICOM output filename");
+  cmd.addParam("cdafile-in", "CDA input filename to be converted");
+  cmd.addParam("dcmfile-out", "DICOM output filename");
   addGeneralOptions(cmd);
   addDocumentOptions(cmd);
   cmd.addSubGroup("override CDA data:");
-      cmd.addOption("--no-override",          "-ov",      "CDA patient and document data must match study,\nseries or manually entered information (default)");
-      cmd.addOption("--override",             "+ov",      "CDA's data will be overwritten by study, series\nor manually entered information");
+  cmd.addOption("--no-override", "-ov",
+                "CDA patient and document data must match study,\nseries or manually entered information (default)");
+  cmd.addOption("--override", "+ov",
+                "CDA's data will be overwritten by study, series\nor manually entered information");
   addOutputOptions(cmd);
 }
 
@@ -496,8 +515,8 @@ void DcmEncapsulatedDocument::addPDFCommandlineOptions(OFCommandLine &cmd)
   ftype = "pdf";
   cmd.setOptionColumns(LONGCOL, SHORTCOL);
   cmd.setParamColumn(LONGCOL + SHORTCOL + 4);
-  cmd.addParam(     "pdffile-in",                         "PDF input filename to be converted");
-  cmd.addParam(     "dcmfile-out",                        "DICOM output filename");
+  cmd.addParam("pdffile-in", "PDF input filename to be converted");
+  cmd.addParam("dcmfile-out", "DICOM output filename");
   addGeneralOptions(cmd);
   addDocumentOptions(cmd);
   addOutputOptions(cmd);
@@ -508,93 +527,94 @@ void DcmEncapsulatedDocument::addSTLCommandlineOptions(OFCommandLine &cmd)
   ftype = "stl";
   cmd.setOptionColumns(LONGCOL, SHORTCOL);
   cmd.setParamColumn(LONGCOL + SHORTCOL + 4);
-  cmd.addParam(     "stlfile-in",                         "STL input filename to be converted");
-  cmd.addParam(     "dcmfile-out",                        "DICOM output filename");
+  cmd.addParam("stlfile-in", "STL input filename to be converted");
+  cmd.addParam("dcmfile-out", "DICOM output filename");
   addGeneralOptions(cmd);
   addDocumentOptions(cmd);
   cmd.addSubGroup("enhanced general equipment:");
-      cmd.addOption("--manufacturer",         "+mn",  1,  "[n]ame: string",
-                                                          "manufacturer's name");
-      cmd.addOption("--manufacturer-model",   "+mm",  1,  "[n]ame: string",
-                                                          "manufacturer's model name");
-      cmd.addOption("--device-serial",        "+ds",  1,  "[n]umber: string",
-                                                          "device serial number");
-      cmd.addOption("--software-versions",    "+sv",  1,  "[v]ersions: string",
-                                                          "software versions");
+  cmd.addOption("--manufacturer", "+mn", 1, "[n]ame: string",
+                "manufacturer's name");
+  cmd.addOption("--manufacturer-model", "+mm", 1, "[n]ame: string",
+                "manufacturer's model name");
+  cmd.addOption("--device-serial", "+ds", 1, "[n]umber: string",
+                "device serial number");
+  cmd.addOption("--software-versions", "+sv", 1, "[v]ersions: string",
+                "software versions");
   cmd.addSubGroup("3d model measurement units:");
-      cmd.addOption("--measurement-units",    "+mu",  3,  "[CSD] [CV] [CM]: string (default: UCUM, um, um)",
-                                                          "measurement units defined by coding scheme\ndesignator CSD, code value CV, code meaning CM");
+  cmd.addOption("--measurement-units", "+mu", 3, "[CSD] [CV] [CM]: string (default: UCUM, um, um)",
+                "measurement units defined by coding scheme\ndesignator CSD, code value CV, code meaning CM");
   addOutputOptions(cmd);
 }
 
 void DcmEncapsulatedDocument::addGeneralOptions(OFCommandLine &cmd)
 {
-  cmd.addGroup(     "general options:", LONGCOL, SHORTCOL + 2);
-    cmd.addOption(  "--help",                 "-h",       "print this help text and exit",          OFCommandLine::AF_Exclusive);
-    cmd.addOption(  "--version",                          "print version information and exit",     OFCommandLine::AF_Exclusive);
+  cmd.addGroup("general options:", LONGCOL, SHORTCOL + 2);
+  cmd.addOption("--help", "-h", "print this help text and exit", OFCommandLine::AF_Exclusive);
+  cmd.addOption("--version", "print version information and exit", OFCommandLine::AF_Exclusive);
   OFLog::addOptions(cmd);
 }
 
 void DcmEncapsulatedDocument::addDocumentOptions(OFCommandLine &cmd)
 {
-  cmd.addGroup(     "DICOM document options:");
-    cmd.addSubGroup("document title:");
-      cmd.addOption("--title",                "+t",   1,  "[t]itle: string (default: empty)",
-                                                          "document title");
-      cmd.addOption("--concept-name",         "+cn",  3,  "[CSD] [CV] [CM]: string (default: empty)",
-                                                          "coded representation of document title defined\nby coding scheme designator CSD,\ncode value CV and code meaning CM");
-    cmd.addSubGroup("patient data:");
-      cmd.addOption("--patient-name",         "+pn",  1,  "[n]ame: string",
-                                                          "patient's name in DICOM PN syntax");
-      cmd.addOption("--patient-id",           "+pi",  1,  "[i]d: string",
-                                                          "patient identifier");
-      cmd.addOption("--patient-birthdate",    "+pb",  1,  "[d]ate: string (YYYYMMDD)",
-                                                          "patient's birth date");
-      cmd.addOption("--patient-sex",          "+ps",  1,  "[s]ex: string (M, F or O)",
-                                                          "patient's sex");
-    cmd.addSubGroup("study and series:");
-      cmd.addOption("--generate",             "+sg",      "generate new study and\nseries UIDs (default)");
-      cmd.addOption("--study-from",           "+st",  1,  "[f]ilename: string",
-                                                          "read patient/study data from DICOM file");
-      cmd.addOption("--series-from",          "+se",  1,  "[f]ilename: string",
-                                                          "read patient/study/series data from DICOM file");
-    cmd.addSubGroup("instance number:");
-      cmd.addOption("--instance-one",         "+i1",      "use instance number 1\n(default, not with +se)");
-      cmd.addOption("--instance-inc",         "+ii",      "increment instance number (only with +se)");
-      cmd.addOption("--instance-set",         "+is",  1,  "[i]nstance number: integer", "use instance number i");
-    cmd.addSubGroup("burned-in annotation:");
-      cmd.addOption("--annotation-yes",       "+an",      "document contains patient identifying data\n(default)");
-      cmd.addOption("--annotation-no",        "-an",      "document does not contain patient identif. data");
+  cmd.addGroup("DICOM document options:");
+  cmd.addSubGroup("document title:");
+  cmd.addOption("--title", "+t", 1, "[t]itle: string (default: empty)",
+                "document title");
+  cmd.addOption("--concept-name", "+cn", 3, "[CSD] [CV] [CM]: string (default: empty)",
+                "coded representation of document title defined\nby coding scheme designator CSD,\n"
+                "code value CV and code meaning CM");
+  cmd.addSubGroup("patient data:");
+  cmd.addOption("--patient-name", "+pn", 1, "[n]ame: string",
+                "patient's name in DICOM PN syntax");
+  cmd.addOption("--patient-id", "+pi", 1, "[i]d: string",
+                "patient identifier");
+  cmd.addOption("--patient-birthdate", "+pb", 1, "[d]ate: string (YYYYMMDD)",
+                "patient's birth date");
+  cmd.addOption("--patient-sex", "+ps", 1, "[s]ex: string (M, F or O)",
+                "patient's sex");
+  cmd.addSubGroup("study and series:");
+  cmd.addOption("--generate", "+sg", "generate new study and\nseries UIDs (default)");
+  cmd.addOption("--study-from", "+st", 1, "[f]ilename: string",
+                "read patient/study data from DICOM file");
+  cmd.addOption("--series-from", "+se", 1, "[f]ilename: string",
+                "read patient/study/series data from DICOM file");
+  cmd.addSubGroup("instance number:");
+  cmd.addOption("--instance-one", "+i1", "use instance number 1\n(default, not with +se)");
+  cmd.addOption("--instance-inc", "+ii", "increment instance number (only with +se)");
+  cmd.addOption("--instance-set", "+is", 1, "[i]nstance number: integer", "use instance number i");
+  cmd.addSubGroup("burned-in annotation:");
+  cmd.addOption("--annotation-yes", "+an", "document contains patient identifying data\n(default)");
+  cmd.addOption("--annotation-no", "-an", "document does not contain patient identif. data");
 }
 
 void DcmEncapsulatedDocument::addOutputOptions(OFCommandLine &cmd)
 {
-  cmd.addGroup(     "processing options:");
-    cmd.addSubGroup("other processing options:");
-      cmd.addOption("--key",                  "-k",   1,  "[k]ey: gggg,eeee=\"str\", path or dict. name=\"str\"",
-                                                          "add further attribute");
-  cmd.addGroup(     "output options:");
-    cmd.addSubGroup("output transfer syntax:");
-      cmd.addOption("--write-xfer-little",    "+te",      "write with explicit VR little endian (default)");
-      cmd.addOption("--write-xfer-big",       "+tb",      "write with explicit VR big endian TS");
-      cmd.addOption("--write-xfer-implicit",  "+ti",      "write with implicit VR little endian TS");
-    cmd.addSubGroup("group length encoding:");
-      cmd.addOption("--group-length-recalc",  "+g=",      "recalculate group lengths if present (default)");
-      cmd.addOption("--group-length-create",  "+g",       "always write with group length elements");
-      cmd.addOption("--group-length-remove",  "-g",       "always write without group length elements");
-    cmd.addSubGroup("length encoding in sequences and items:");
-      cmd.addOption("--length-explicit",      "+e",       "write with explicit lengths (default)");
-      cmd.addOption("--length-undefined",     "-e",       "write with undefined lengths");
-    cmd.addSubGroup("data set trailing padding (not with --write-dataset):");
-      cmd.addOption("--padding-retain",       "-p=",      "do not change padding (default)");
-      cmd.addOption("--padding-off",          "-p",       "no padding (implicit if --write-dataset)");
-      cmd.addOption("--padding-create",       "+p",   2,  "[f]ile-pad [i]tem-pad: integer",
-                                                          "align file on multiple of f bytes\nand items on multiple of i bytes");
+  cmd.addGroup("processing options:");
+  cmd.addSubGroup("other processing options:");
+  cmd.addOption("--key", "-k", 1, "[k]ey: gggg,eeee=\"str\", path or dict. name=\"str\"",
+                "add further attribute");
+  cmd.addGroup("output options:");
+  cmd.addSubGroup("output transfer syntax:");
+  cmd.addOption("--write-xfer-little", "+te", "write with explicit VR little endian (default)");
+  cmd.addOption("--write-xfer-big", "+tb", "write with explicit VR big endian TS");
+  cmd.addOption("--write-xfer-implicit", "+ti", "write with implicit VR little endian TS");
+  cmd.addSubGroup("group length encoding:");
+  cmd.addOption("--group-length-recalc", "+g=", "recalculate group lengths if present (default)");
+  cmd.addOption("--group-length-create", "+g", "always write with group length elements");
+  cmd.addOption("--group-length-remove", "-g", "always write without group length elements");
+  cmd.addSubGroup("length encoding in sequences and items:");
+  cmd.addOption("--length-explicit", "+e", "write with explicit lengths (default)");
+  cmd.addOption("--length-undefined", "-e", "write with undefined lengths");
+  cmd.addSubGroup("data set trailing padding (not with --write-dataset):");
+  cmd.addOption("--padding-retain", "-p=", "do not change padding (default)");
+  cmd.addOption("--padding-off", "-p", "no padding (implicit if --write-dataset)");
+  cmd.addOption("--padding-create", "+p", 2, "[f]ile-pad [i]tem-pad: integer",
+                "align file on multiple of f bytes\nand items on multiple of i bytes");
 }
 
 void DcmEncapsulatedDocument::parseArguments(
-  OFConsoleApplication& app,
-  OFCommandLine& cmd)
+        OFConsoleApplication &app,
+        OFCommandLine &cmd)
 {
   //command line parameters and options
   cmd.getParam(1, opt_ifname);
@@ -640,13 +660,13 @@ void DcmEncapsulatedDocument::parseArguments(
   {
     app.checkValue(cmd.getValue(opt_patientName));
     app.checkConflict("--patient-name", "--study-from or --series-from",
-                        opt_seriesFile != "");
+                      opt_seriesFile != "");
   }
   if (cmd.findOption("--patient-id"))
   {
     app.checkValue(cmd.getValue(opt_patientID));
     app.checkConflict("--patient-id", "--study-from or --series-from",
-                        opt_seriesFile != "");
+                      opt_seriesFile != "");
   }
   if (cmd.findOption("--patient-birthdate"))
   {
@@ -715,14 +735,14 @@ void DcmEncapsulatedDocument::parseArguments(
   if (cmd.findOption("--padding-retain"))
   {
     app.checkConflict("--padding-retain", "--write-dataset",
-                        opt_writeMode == EWM_dataset);
+                      opt_writeMode == EWM_dataset);
     opt_opadenc = EPD_noChange;
   }
   if (cmd.findOption("--padding-off")) opt_opadenc = EPD_withoutPadding;
   if (cmd.findOption("--padding-create"))
   {
     app.checkConflict("--padding-create", "--write-dataset",
-                        opt_writeMode == EWM_dataset);
+                      opt_writeMode == EWM_dataset);
     app.checkValue(cmd.getValueAndCheckMin(opt_filepad, 0));
     app.checkValue(cmd.getValueAndCheckMin(opt_itempad, 0));
     opt_opadenc = EPD_withPadding;
@@ -730,17 +750,18 @@ void DcmEncapsulatedDocument::parseArguments(
   cmd.endOptionBlock();
 
   // create override attribute dataset (copied from findscu code)
-  if (cmd.findOption("--key", 0, OFCommandLine::FOM_FirstFromLeft ) )
+  if (cmd.findOption("--key", 0, OFCommandLine::FOM_FirstFromLeft))
   {
     const char *ovKey = NULL;
-    do {
+    do
+    {
       app.checkValue(cmd.getValue(ovKey));
       overrideKeys.push_back(ovKey);
-    } while (cmd.findOption("--key", 0, OFCommandLine::FOM_NextFromLeft ) );
+    } while (cmd.findOption("--key", 0, OFCommandLine::FOM_NextFromLeft));
   }
   DcmEncapsulatedDocument::setOverrideKeys(overrideKeys);
   // initialize default for --series-from
-  if (opt_seriesFile!="" && opt_readSeriesInfo) opt_increment = OFTrue;
+  if (opt_seriesFile != "" && opt_readSeriesInfo) opt_increment = OFTrue;
 
   cmd.beginOptionBlock();
   if (cmd.findOption("--instance-one"))
@@ -764,7 +785,7 @@ void DcmEncapsulatedDocument::parseArguments(
   cmd.endOptionBlock();
 }
 
-OFCondition DcmEncapsulatedDocument::createIdentifiers(OFLoggerappLogger)
+OFCondition DcmEncapsulatedDocument::createIdentifiers(OFLogger &appLogger)
 {
   char buf[100];
   OFCondition cond = EC_Normal;
@@ -776,7 +797,7 @@ OFCondition DcmEncapsulatedDocument::createIdentifiers(OFLogger& appLogger)
     if (cond.bad())
     {
       OFLOG_WARN(appLogger, cond.text()
-                  << ": reading file: " << opt_seriesFile);
+              << ": reading file: " << opt_seriesFile);
     }
     else
     {
@@ -788,28 +809,28 @@ OFCondition DcmEncapsulatedDocument::createIdentifiers(OFLogger& appLogger)
         c = NULL;
         if (dset->findAndGetString(DCM_PatientName, c).good() && c)
         {
-        opt_patientName = c;
+          opt_patientName = c;
         }
         c = NULL;
         if (dset->findAndGetString(DCM_PatientID, c).good() && c)
         {
-        opt_patientID = c;
+          opt_patientID = c;
         }
         c = NULL;
         if (dset->findAndGetString(DCM_PatientBirthDate, c).good() && c)
         {
-        opt_patientBirthdate = c;
+          opt_patientBirthdate = c;
         }
         c = NULL;
         if (dset->findAndGetString(DCM_PatientSex, c).good() && c)
         {
-        opt_patientSex = c;
+          opt_patientSex = c;
         }
         OFLOG_TRACE(appLogger, "reading study attributes");
         c = NULL;
         if (dset->findAndGetString(DCM_StudyInstanceUID, c).good() && c)
         {
-        opt_studyUID = c;
+          opt_studyUID = c;
         }
         OFLOG_TRACE(appLogger, "reading series attributes");
         if (opt_readSeriesInfo)
@@ -817,10 +838,10 @@ OFCondition DcmEncapsulatedDocument::createIdentifiers(OFLogger& appLogger)
           c = NULL;
           if (dset->findAndGetString(DCM_SeriesInstanceUID, c).good() && c)
           {
-          opt_seriesUID = c;
+            opt_seriesUID = c;
           }
           if (dset->findAndGetSint32(DCM_InstanceNumber,
-                                      incrementedInstance).good())
+                                     incrementedInstance).good())
           {
             ++incrementedInstance;
           }
@@ -888,8 +909,8 @@ OFCondition DcmEncapsulatedDocument::createIdentifiers(OFLogger& appLogger)
 }
 
 int DcmEncapsulatedDocument::insertEncapsulatedDocument(
-  DcmItem *dataset,
-  OFLogger& appLogger)
+        DcmItem *dataset,
+        OFLogger &appLogger)
 {
   char buf[100];
   size_t fileSize = 0;
@@ -950,13 +971,13 @@ int DcmEncapsulatedDocument::insertEncapsulatedDocument(
     if (!found)
     {
       OFLOG_ERROR(appLogger, "file " << opt_ifname
-        << ": unable to decode PDF version number");
+              << ": unable to decode PDF version number");
       fclose(encapfile);
       return EXITCODE_INVALID_INPUT_FILE;
     }
     OFLOG_INFO(appLogger, "file " << opt_ifname
-      << ": PDF " << version << ", "
-      << (fileSize + 1023) / 1024 << "kB");
+            << ": PDF " << version << ", "
+            << (fileSize + 1023) / 1024 << "kB");
   }
   else
   {
@@ -964,8 +985,8 @@ int DcmEncapsulatedDocument::insertEncapsulatedDocument(
     {
       //xml validation occurs when getting data
       OFLOG_INFO(appLogger, "file " << opt_ifname
-        << ": HL7 CDA file (XML Format)" << ", "
-        << (fileSize + 1023) / 1024 << "kB");
+              << ": HL7 CDA file (XML Format)" << ", "
+              << (fileSize + 1023) / 1024 << "kB");
     }
     else
     {
@@ -977,17 +998,17 @@ int DcmEncapsulatedDocument::insertEncapsulatedDocument(
         //  - AttributeCount: 1 short (2 bytes)
         // Total: 50 bytes per facet
         const size_t facetSize32 = 3 * sizeof(Float32)
-          + 3 * 3 * sizeof(Float32)
-          + sizeof(Uint16);
+                                   + 3 * 3 * sizeof(Float32)
+                                   + sizeof(Uint16);
         const size_t facetSize64 = 3 * sizeof(Float64)
-          + 3 * 3 * sizeof(Float64)
-          + sizeof(Uint16);
+                                   + 3 * 3 * sizeof(Float64)
+                                   + sizeof(Uint16);
         // STL validation for ASCII CODE
         if (fileSize < 15)
         {
           // "solid " and "endsolid " markers for an ASCII file
           OFLOG_ERROR(appLogger, "The STL file is not long enough"
-            << " (" << fileSize << "kB)");
+                  << " (" << fileSize << "kB)");
           fclose(encapfile);
           return EXITCODE_INVALID_INPUT_FILE;
         }
@@ -1000,22 +1021,22 @@ int DcmEncapsulatedDocument::insertEncapsulatedDocument(
         if (0 == strncmp("solid ", buf, 6))
         {
           OFLOG_ERROR(appLogger, "File " << opt_ifname
-            << " starts with 'solid '. "
-            << "It is a valid STL file but it is in ASCII Code"
-            << "and DICOM only accepts binary STL");
+                  << " starts with 'solid '. "
+                  << "It is a valid STL file but it is in ASCII Code"
+                  << "and DICOM only accepts binary STL");
           return EXITCODE_INVALID_INPUT_FILE;
         }
-        //////STL validation for Binary Format
+          //////STL validation for Binary Format
         else
         {
           OFLOG_DEBUG(appLogger, "Magic word 'solid ' not found. "
-            << "Validating STL file "
-            << "in Binary format");
+                  << "Validating STL file "
+                  << "in Binary format");
           // 80-byte header + 4-byte "number of triangles" for a binary file
           if (fileSize < 84)
           {
             OFLOG_ERROR(appLogger, "The binary STL file is not long enough"
-              << " (" << fileSize << "kB)");
+                    << " (" << fileSize << "kB)");
             fclose(encapfile);
             return EXITCODE_INVALID_INPUT_FILE;
           }
@@ -1025,39 +1046,39 @@ int DcmEncapsulatedDocument::insertEncapsulatedDocument(
           for (int j = 0; j < 4; j++)
             ntriangleschar[j] = buf[80 + j];
           ntriangleschar[4] = 0;
-          Uint32nTriangles = OFreinterpret_cast(Uint32*, ntriangleschar);
+          Uint32 *nTriangles = OFreinterpret_cast(Uint32*, ntriangleschar);
           // Verify that file size equals the sum of
           // header + nTriangles value + all triangles
           OFLOG_DEBUG(appLogger, "verifying if the file size is consistent");
           if (fileSize == (84 + *OFconst_cast(Uint32*, nTriangles) * facetSize32) ||
-            fileSize == (84 + *OFconst_cast(Uint32*, nTriangles) * facetSize64))
+              fileSize == (84 + *OFconst_cast(Uint32*, nTriangles) * facetSize64))
           {
             OFLOG_DEBUG(appLogger, "File " << opt_ifname
-              << " passed binary STL validation." << OFendl
-              << "Assuming valid STL file "
-              << "in binary format"
+                    << " passed binary STL validation." << OFendl
+                    << "Assuming valid STL file "
+                    << "in binary format"
             );
             OFLOG_TRACE(appLogger, "The binary STL file is:" << OFendl
-              << fileSize << " kB " << " as expected." << OFendl
-              << (84 + *OFconst_cast(Uint32*, nTriangles) * facetSize32) << " kB for x86" << OFendl
-              << (84 + *OFconst_cast(Uint32*, nTriangles) * facetSize64) << " kB for x64" << OFendl
-              << "(84 + triangles number * facet size)" << OFendl
-              << " number of Triangles " << *OFconst_cast(Uint32*, nTriangles) << OFendl
-              << " nTriangles (Uint32): " << nTriangles << OFendl
-              << " facetSize32: " << facetSize32 << OFendl
-              << " facetSize64: " << facetSize64 << OFendl
+                    << fileSize << " kB " << " as expected." << OFendl
+                    << (84 + *OFconst_cast(Uint32 * , nTriangles) * facetSize32) << " kB for x86" << OFendl
+                    << (84 + *OFconst_cast(Uint32 * , nTriangles) * facetSize64) << " kB for x64" << OFendl
+                    << "(84 + triangles number * facet size)" << OFendl
+                    << " number of Triangles " << *OFconst_cast(Uint32 * , nTriangles) << OFendl
+                    << " nTriangles (Uint32): " << nTriangles << OFendl
+                    << " facetSize32: " << facetSize32 << OFendl
+                    << " facetSize64: " << facetSize64 << OFendl
             );
           }
           else
           {
             OFLOG_ERROR(appLogger, "The binary STL file is not consistent." << OFendl
-              << (84 + *OFconst_cast(Uint32*, nTriangles) * facetSize32) << " kB for x86 and "
-              << (84 + *OFconst_cast(Uint32*, nTriangles) * facetSize64) << " kB for x64 " << OFendl
-              << "(84 + triangles number * facet size)" << OFendl
-              << " number of Triangles " << *OFconst_cast(Uint32*, nTriangles) << OFendl
-              << " nTriangles (Uint32): " << nTriangles << OFendl
-              << " facetSize32: " << facetSize32 << OFendl
-              << " facetSize64: " << facetSize64 << OFendl
+                    << (84 + *OFconst_cast(Uint32 * , nTriangles) * facetSize32) << " kB for x86 and "
+                    << (84 + *OFconst_cast(Uint32 * , nTriangles) * facetSize64) << " kB for x64 " << OFendl
+                    << "(84 + triangles number * facet size)" << OFendl
+                    << " number of Triangles " << *OFconst_cast(Uint32 * , nTriangles) << OFendl
+                    << " nTriangles (Uint32): " << nTriangles << OFendl
+                    << " facetSize32: " << facetSize32 << OFendl
+                    << " facetSize64: " << facetSize64 << OFendl
             );
             fclose(encapfile);
             return EXITCODE_INVALID_INPUT_FILE;
@@ -1067,7 +1088,7 @@ int DcmEncapsulatedDocument::insertEncapsulatedDocument(
       else
       {
         OFLOG_WARN(appLogger, "Filetype not supported or filetype not set. Current ftype is " << ftype << OFendl
-          << "The name of the passed logger is: " << appLogger.getName());
+                << "The name of the passed logger is: " << appLogger.getName());
       }
     }
   }
@@ -1082,9 +1103,18 @@ int DcmEncapsulatedDocument::insertEncapsulatedDocument(
   if (elem)
   {
     size_t numBytes = fileSize;
+    // according to CP 1851
+    result = dataset->putAndInsertUint32(DCM_EncapsulatedDocumentLength, OFstatic_cast(Uint32, numBytes));
     if (numBytes & 1) ++numBytes;
     Uint8 *bytes = NULL;
-    result = elem->createUint8Array(OFstatic_cast(Uint32, numBytes), bytes);
+    if (result.good())
+    {
+      result = elem->createUint8Array(OFstatic_cast(Uint32, numBytes), bytes);
+    }
+    else
+    {
+      return EXITCODE_CANNOT_WRITE_OUTPUT_FILE;
+    }
     if (result.good())
     {
       // blank pad byte
@@ -1096,6 +1126,10 @@ int DcmEncapsulatedDocument::insertEncapsulatedDocument(
         return EXITCODE_CANNOT_READ_INPUT_FILE;
       }
     }
+    else
+    {
+      return EXITCODE_MEMORY_EXHAUSTED;
+    }
   }
   else
   {
@@ -1126,8 +1160,8 @@ int DcmEncapsulatedDocument::insertEncapsulatedDocument(
 }
 
 OFCondition DcmEncapsulatedDocument::createHeader(
-  DcmItem *dataset,
-  OFLogger& logger)
+        DcmItem *dataset,
+        OFLogger &logger)
 {
   OFCondition result = EC_Normal;
   char buf[80];
@@ -1143,7 +1177,7 @@ OFCondition DcmEncapsulatedDocument::createHeader(
   if (result.good()) result = dataset->insertEmptyElement(DCM_AcquisitionDateTime);
   if (result.good())
   {
-    if (opt_conceptCSD!="" && opt_conceptCV != "" && opt_conceptCM != "")
+    if (opt_conceptCSD != "" && opt_conceptCV != "" && opt_conceptCM != "")
     {
       result = DcmCodec::insertCodeSequence(dataset, DCM_ConceptNameCodeSequence,
                                             opt_conceptCSD.c_str(),
@@ -1158,7 +1192,7 @@ OFCondition DcmEncapsulatedDocument::createHeader(
   // insert const value attributes
   if (result.good())
   {
-  result = dataset->putAndInsertString(DCM_SpecificCharacterSet, "ISO_IR 100");
+    result = dataset->putAndInsertString(DCM_SpecificCharacterSet, "ISO_IR 100");
   }
   //insert encapsulated file storage UID (CDA/PDF/STL)
   if (result.good())
@@ -1179,9 +1213,9 @@ OFCondition DcmEncapsulatedDocument::createHeader(
       if (opt_frameOfReferenceUID.empty())
       {
         OFLOG_DEBUG(logger, "Frame of Reference UID "
-                    << DCM_FrameOfReferenceUID
-                    << " value was empty, generating a new one."
-                      );
+                << DCM_FrameOfReferenceUID
+                << " value was empty, generating a new one."
+        );
         dcmGenerateUniqueIdentifier(buf, SITE_SERIES_UID_ROOT);
         opt_frameOfReferenceUID = buf;
       }
@@ -1190,9 +1224,9 @@ OFCondition DcmEncapsulatedDocument::createHeader(
         if (DcmUniqueIdentifier::checkStringValue(opt_frameOfReferenceUID, "1").bad())
         {
           OFLOG_DEBUG(logger, "Frame of Reference UID "
-                      << DCM_FrameOfReferenceUID
-                      << " value was faulty, generating a new one."
-                        );
+                  << DCM_FrameOfReferenceUID
+                  << " value was faulty, generating a new one."
+          );
           dcmGenerateUniqueIdentifier(buf, SITE_SERIES_UID_ROOT);
           opt_frameOfReferenceUID = buf;
         }
@@ -1202,20 +1236,21 @@ OFCondition DcmEncapsulatedDocument::createHeader(
         OFLOG_TRACE(logger, "Inserting Frame of Reference info to dataset");
         result = dataset->putAndInsertOFStringArray(DCM_FrameOfReferenceUID, opt_frameOfReferenceUID);
       }
-      if (result.good())result = dataset->putAndInsertOFStringArray(DCM_PositionReferenceIndicator, opt_positionReferenceIndicator);
+      if (result.good())
+        result = dataset->putAndInsertOFStringArray(DCM_PositionReferenceIndicator, opt_positionReferenceIndicator);
       OFLOG_TRACE(logger, "Validating and inserting Enhanced General Equipment fields");
       if (result.good())
       {
         if (opt_manufacturer.empty())
         {
-          opt_manufacturer="DCMTK_MANUFACTURING";
+          opt_manufacturer = "DCMTK_MANUFACTURING";
           OFLOG_WARN(logger, "No Manufacturer "
-                      << DCM_Manufacturer
-                      << " provided nor found in series. This attribute is "
-                      << "required for Enhanced General Equipment module. "
-                      << opt_manufacturer
-                      << " will be inserted as dummy value."
-                        );
+                  << DCM_Manufacturer
+                  << " provided nor found in series. This attribute is "
+                  << "required for Enhanced General Equipment module. "
+                  << opt_manufacturer
+                  << " will be inserted as dummy value."
+          );
         }
         result = dataset->putAndInsertOFStringArray(DCM_Manufacturer, opt_manufacturer);
       }
@@ -1223,14 +1258,14 @@ OFCondition DcmEncapsulatedDocument::createHeader(
       {
         if (opt_manufacturerModelName.empty())
         {
-          opt_manufacturerModelName="DCMTK_3DMODEL_3";
+          opt_manufacturerModelName = "DCMTK_3DMODEL_3";
           OFLOG_WARN(logger, "No Manufacturer Model Name "
-                      << DCM_ManufacturerModelName
-                      << " provided nor found in series. This attribute is "
-                      << "required for Enhanced General Equipment module. "
-                      << opt_manufacturerModelName
-                      << " will be inserted as dummy value."
-                        );
+                  << DCM_ManufacturerModelName
+                  << " provided nor found in series. This attribute is "
+                  << "required for Enhanced General Equipment module. "
+                  << opt_manufacturerModelName
+                  << " will be inserted as dummy value."
+          );
         }
         result = dataset->putAndInsertOFStringArray(DCM_ManufacturerModelName, opt_manufacturerModelName);
       }
@@ -1238,14 +1273,14 @@ OFCondition DcmEncapsulatedDocument::createHeader(
       {
         if (opt_deviceSerialNumber.empty())
         {
-          opt_deviceSerialNumber="DCMTK01234567890";
+          opt_deviceSerialNumber = "DCMTK01234567890";
           OFLOG_WARN(logger, "No Device Serial Number "
-                      << DCM_DeviceSerialNumber
-                      << " provided nor found in series. This attribute is "
-                      << "required for Enhanced General Equipment module. "
-                      << opt_deviceSerialNumber
-                      << " will be inserted as dummy value."
-                        );
+                  << DCM_DeviceSerialNumber
+                  << " provided nor found in series. This attribute is "
+                  << "required for Enhanced General Equipment module. "
+                  << opt_deviceSerialNumber
+                  << " will be inserted as dummy value."
+          );
         }
         result = dataset->putAndInsertOFStringArray(DCM_DeviceSerialNumber, opt_deviceSerialNumber);
       }
@@ -1253,14 +1288,14 @@ OFCondition DcmEncapsulatedDocument::createHeader(
       {
         if (opt_softwareVersions.empty())
         {
-          opt_softwareVersions=OFFIS_DCMTK_VERSION;
+          opt_softwareVersions = OFFIS_DCMTK_VERSION;
           OFLOG_WARN(logger, "No Software Versions "
-                      << DCM_SoftwareVersions
-                      << " provided nor found in series. This attribute is "
-                      << "required for Enhanced General Equipment module. "
-                      << opt_softwareVersions
-                      << " will be inserted as dummy value."
-                        );
+                  << DCM_SoftwareVersions
+                  << " provided nor found in series. This attribute is "
+                  << "required for Enhanced General Equipment module. "
+                  << opt_softwareVersions
+                  << " will be inserted as dummy value."
+          );
         }
         result = dataset->putAndInsertOFStringArray(DCM_SoftwareVersions, opt_softwareVersions);
       }
@@ -1269,17 +1304,17 @@ OFCondition DcmEncapsulatedDocument::createHeader(
         if (opt_measurementUnitsCSD != "" && opt_measurementUnitsCV != "" && opt_measurementUnitsCM != "")
         {
           result = DcmCodec::insertCodeSequence(dataset, DCM_MeasurementUnitsCodeSequence,
-            opt_measurementUnitsCSD.c_str(),
-            opt_measurementUnitsCV.c_str(),
-            opt_measurementUnitsCM.c_str());
+                                                opt_measurementUnitsCSD.c_str(),
+                                                opt_measurementUnitsCV.c_str(),
+                                                opt_measurementUnitsCM.c_str());
         }
         else
         {
           OFLOG_DEBUG(logger, "Measurement Units Code Sequence "
-                      << DCM_FrameOfReferenceUID
-                      << "had one or more empty values, generating default values."
-                        );
-          result = DcmCodec::insertCodeSequence(dataset, DCM_MeasurementUnitsCodeSequence, "UCUM","um","um");
+                  << DCM_FrameOfReferenceUID
+                  << "had one or more empty values, generating default values."
+          );
+          result = DcmCodec::insertCodeSequence(dataset, DCM_MeasurementUnitsCodeSequence, "UCUM", "um", "um");
         }
       }
       if (result.good())
@@ -1291,7 +1326,7 @@ OFCondition DcmEncapsulatedDocument::createHeader(
   }
   if (result.good())
   {
-    if (ftype=="stl")
+    if (ftype == "stl")
     {
       result = dataset->putAndInsertString(DCM_Modality, "M3D");
     }
@@ -1317,13 +1352,13 @@ OFCondition DcmEncapsulatedDocument::createHeader(
   if (result.good())
   {
     // according to C.24.2.1 on part 3, (0042,0012) is text/XML for CDA.
-    if (ftype=="cda")
+    if (ftype == "cda")
       result = dataset->putAndInsertString(DCM_MIMETypeOfEncapsulatedDocument, "text/XML");
     // according to A.45.1.4.1 on part 3, MIME Type is application/pdf for PDF.
-    if (ftype=="pdf")
+    if (ftype == "pdf")
       result = dataset->putAndInsertString(DCM_MIMETypeOfEncapsulatedDocument, "application/pdf");
     // according to A.85.1.4.2 on part 3, MIME Type is model/stl.
-    if (ftype=="stl")
+    if (ftype == "stl")
       result = dataset->putAndInsertString(DCM_MIMETypeOfEncapsulatedDocument, "model/stl");
   }
   // there is no way we could determine a meaningful series number, so we just use a constant.
@@ -1335,11 +1370,11 @@ OFCondition DcmEncapsulatedDocument::createHeader(
   if (result.good()) result = dataset->putAndInsertString(DCM_PatientBirthDate, opt_patientBirthdate.c_str());
   if (result.good()) result = dataset->putAndInsertString(DCM_PatientSex, opt_patientSex.c_str());
   if (result.good()) result = dataset->putAndInsertString(DCM_BurnedInAnnotation, opt_annotation ? "YES" : "NO");
-  if (strlen(cda_mediaTypes.c_str()) >0)
+  if (strlen(cda_mediaTypes.c_str()) > 0)
   {
     if (result.good()) result = dataset->putAndInsertString(DCM_ListOfMIMETypes, cda_mediaTypes.c_str());
   }
-  if (hl7_InstanceIdentifier.size() >0)
+  if (hl7_InstanceIdentifier.size() > 0)
   {
     if (result.good()) result = dataset->putAndInsertString(DCM_HL7InstanceIdentifier, hl7_InstanceIdentifier.c_str());
   }
@@ -1371,7 +1406,10 @@ OFCondition DcmEncapsulatedDocument::applyOverrideKeys(DcmDataset *outputDset)
     if (cond.bad())
     {
       OFString err;
-      err += "Bad override key/path: "; err += *path; err += ": "; err += cond.text();
+      err += "Bad override key/path: ";
+      err += *path;
+      err += ": ";
+      err += cond.text();
       return makeOFCondition(OFM_dcmdata, 18, OF_error, err.c_str());
     }
     path++;
@@ -1379,7 +1417,7 @@ OFCondition DcmEncapsulatedDocument::applyOverrideKeys(DcmDataset *outputDset)
   return cond;
 }
 
-void DcmEncapsulatedDocument::setOverrideKeys(const OFList<OFString>ovkeys)
+void DcmEncapsulatedDocument::setOverrideKeys(const OFList<OFString> &ovkeys)
 {
   OFListConstIterator(OFString) it = ovkeys.begin();
   OFListConstIterator(OFString) end = ovkeys.end();
@@ -1393,8 +1431,8 @@ void DcmEncapsulatedDocument::setOverrideKeys(const OFList<OFString>& ovkeys)
 OFCondition DcmEncapsulatedDocument::saveFile(DcmFileFormat fileformat)
 {
   return fileformat.saveFile(opt_ofname, opt_oxfer, opt_oenctype, opt_oglenc,
-                              opt_opadenc, OFstatic_cast(Uint32, opt_filepad),
-                              OFstatic_cast(Uint32, opt_itempad));
+                             opt_opadenc, OFstatic_cast(Uint32, opt_filepad),
+                             OFstatic_cast(Uint32, opt_itempad));
 }
 
 OFString DcmEncapsulatedDocument::getInputFileName()
@@ -1404,7 +1442,7 @@ OFString DcmEncapsulatedDocument::getInputFileName()
 
 void DcmEncapsulatedDocument::setInputFileName(OFString fName)
 {
-  opt_ifname= fName;
+  opt_ifname = fName;
 }
 
 OFString DcmEncapsulatedDocument::getOutputFileName()
index be125dd7bae0b1682b60681e51d586dad73fa1c0..538cf498130a04104217076e11b5171d79bd67dd 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -62,22 +62,23 @@ makeOFConditionConst(EC_SequDelimitationItemMissing,     OFM_dcmdata, 34, OF_err
 // error code 37 is reserved for XML conversion error messages (see below)
 makeOFConditionConst(EC_ItemDelimitationItemMissing,     OFM_dcmdata, 38, OF_error, "Item Delimitation Item missing"             );
 makeOFConditionConst(EC_PrematureSequDelimitationItem,   OFM_dcmdata, 39, OF_error, "Sequence Delimitation Item occurred before Item was completely read" );
-makeOFConditionConst(EC_InvalidDICOMDIR,                 OFM_dcmdata, 40, OF_error, "Invalid DICOMDIR" );
+makeOFConditionConst(EC_InvalidDICOMDIR,                 OFM_dcmdata, 40, OF_error, "Invalid DICOMDIR"                           );
 makeOFConditionConst(EC_UnknownVR,                       OFM_dcmdata, 41, OF_error, "Unknown VR: Tag not found in data dictionary" );
-makeOFConditionConst(EC_InvalidValue,                    OFM_dcmdata, 42, OF_error, "Invalid Value");
-makeOFConditionConst(EC_ItemNotFound,                    OFM_dcmdata, 43, OF_error, "Item not found");
-makeOFConditionConst(EC_UnknownTransferSyntax,           OFM_dcmdata, 44, OF_error, "Unknown Transfer Syntax");
-makeOFConditionConst(EC_CannotCheck,                     OFM_dcmdata, 45, OF_error, "Cannot perform check");
-makeOFConditionConst(EC_MissingValue,                    OFM_dcmdata, 46, OF_error, "Missing value");
-makeOFConditionConst(EC_MissingAttribute,                OFM_dcmdata, 47, OF_error, "Missing attribute");
-makeOFConditionConst(EC_InternalError,                   OFM_dcmdata, 48, OF_error, "Internal error");
-makeOFConditionConst(EC_InvalidCharacter,                OFM_dcmdata, 49, OF_error, "Invalid character");
+makeOFConditionConst(EC_InvalidValue,                    OFM_dcmdata, 42, OF_error, "Invalid Value"                              );
+makeOFConditionConst(EC_ItemNotFound,                    OFM_dcmdata, 43, OF_error, "Item not found"                             );
+makeOFConditionConst(EC_UnknownTransferSyntax,           OFM_dcmdata, 44, OF_error, "Unknown Transfer Syntax"                    );
+makeOFConditionConst(EC_CannotCheck,                     OFM_dcmdata, 45, OF_error, "Cannot perform check"                       );
+makeOFConditionConst(EC_MissingValue,                    OFM_dcmdata, 46, OF_error, "Missing value"                              );
+makeOFConditionConst(EC_MissingAttribute,                OFM_dcmdata, 47, OF_error, "Missing attribute"                          );
+makeOFConditionConst(EC_InternalError,                   OFM_dcmdata, 48, OF_error, "Internal error"                             );
+makeOFConditionConst(EC_InvalidCharacter,                OFM_dcmdata, 49, OF_error, "Invalid character"                          );
 // error code 50 is reserved for determine start fragment error messages (see below)
-makeOFConditionConst(EC_UndefinedLengthOBOW,             OFM_dcmdata, 51, OF_error, "Illegal element with OB or OW Value Representation and undefined length encountered");
-makeOFConditionConst(EC_VOI_LUT_OBOW,                    OFM_dcmdata, 52, OF_error, "Illegal VOI LUT Sequence element with OB or OW Value Representation and explicit length encountered");
-makeOFConditionConst(EC_PixelDataExplLengthIllegal,      OFM_dcmdata, 53, OF_error, "Pixel data in top level dataset in compressed Transfer Syntax uses explicit length");
+makeOFConditionConst(EC_UndefinedLengthOBOW,             OFM_dcmdata, 51, OF_error, "Illegal element with OB or OW Value Representation and undefined length encountered" );
+makeOFConditionConst(EC_VOI_LUT_OBOW,                    OFM_dcmdata, 52, OF_error, "Illegal VOI LUT Sequence element with OB or OW Value Representation and explicit length encountered" );
+makeOFConditionConst(EC_PixelDataExplLengthIllegal,      OFM_dcmdata, 53, OF_error, "Pixel data in top level dataset in compressed Transfer Syntax uses explicit length" );
 makeOFConditionConst(EC_ElemLengthExceeds32BitField,     OFM_dcmdata, 54, OF_error, "Length of element value exceeds maximum of 32-bit length field" );
-
+makeOFConditionConst(EC_CannotWriteJsonNumber,           OFM_dcmdata, 55, OF_error, "Cannot write 'nan' or 'inf' as JSON number" );
+makeOFConditionConst(EC_CannotWriteJsonInlineBinary,     OFM_dcmdata, 56, OF_error, "JSON InlineBinary encoding not supported for compressed pixel data" );
 
 const unsigned short EC_CODE_CannotSelectCharacterSet     = 35;
 const unsigned short EC_CODE_CannotConvertCharacterSet    = 36;
index 452ff97ef6e8954e0403259205877de83ebb6d5d..4b6b648993213da26a4dfb9fd0e5b31b8074d519 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -39,6 +39,7 @@
 #include "dcmtk/dcmdata/dcvrus.h"
 #include "dcmtk/dcmdata/dcvrae.h"
 #include "dcmtk/dcmdata/dcvrsh.h"
+#include "dcmtk/dcmdata/dcvrur.h"
 #include "dcmtk/dcmdata/dcmetinf.h"
 
 #include "dcmtk/dcmdata/dcdeftag.h"
@@ -231,46 +232,38 @@ OFCondition DcmFileFormat::writeXML(STD_NAMESPACE ostream &out,
 OFCondition DcmFileFormat::writeJson(STD_NAMESPACE ostream &out,
                                      DcmJsonFormat &format)
 {
-    if (format.printMetaheaderInformation)
+    OFBool meta = format.printMetaheaderInformation;
+    DcmDataset *dset = getDataset();
+    OFCondition status = EC_Normal;
+    if (meta)
     {
-        if (!itemList->empty())
+        // print out meta-header elements and dataset (non-standard)
+        DcmMetaInfo *metinf = getMetaInfo();
+        out << format.indent() << "{" << format.newline();
+        if (metinf)
         {
-            out << format.indent() << "{" << format.newline();
-            // write content of all children (DcmObject)
-            itemList->seek(ELP_first);
-            OFCondition status = EC_Normal;
-            status = itemList->get()->writeJson(out, format);
-            while (status.good() && itemList->seek(ELP_next))
-            {
-                out << "," << format.newline();
-                status = itemList->get()->writeJson(out, format);
-            }
-            out << format.newline() << format.indent() << "}" << format.newline();
-            return status;
+          status = metinf->writeJsonExt(out, format, OFFalse, OFFalse);
+          out << format.newline();
         }
-        else
+        if (dset && status.good())
         {
-            return EC_CorruptedData;
+            status = dset->writeJsonExt(out, format, OFFalse, OFFalse);
         }
+        out << format.newline() << format.indent() << "}" << format.newline();
     }
     else
     {
-        if (DcmDataset *dset = getDataset())
+        // standard case: only print dataset
+        if (dset)
         {
-            out << format.indent() << "{" << format.newline();
-            OFCondition status = EC_Normal;
-            // write content of dataset
-            status = dset->writeJson(out, format);
-            out << format.newline() << format.indent() << "}" << format.newline();
-            return status;
+            status = dset->writeJsonExt(out, format, OFTrue, OFTrue);
         }
         else
         {
             out << format.indent() << "{}" << format.newline();
-            return EC_Normal;
         }
     }
-    return EC_Normal;
+    return status;
 }
 
 
@@ -509,6 +502,17 @@ OFCondition DcmFileFormat::checkMetaHeaderValue(DcmMetaInfo *metainfo,
             }
             DCMDATA_WARN("DcmFileFormat: Don't know how to handle " << tag.getTagName());
         }
+        else if ((xtag == DCM_SourcePresentationAddress) ||  // (0002,0026)
+                 (xtag == DCM_SendingPresentationAddress) || // (0002,0027)
+                 (xtag == DCM_ReceivingPresentationAddress)) // (0002,0028)
+        {
+            if (elem == NULL)
+            {
+                elem = new DcmUniversalResourceIdentifierOrLocator(tag);
+                metainfo->insert(elem, OFTrue);
+            }
+            DCMDATA_WARN("DcmFileFormat: Don't know how to handle " << tag.getTagName());
+        }
         else if (xtag == DCM_PrivateInformationCreatorUID)  // (0002,0100)
         {
             if (elem == NULL)
index 1a62caf9c172aa38a9c1a44afc8862859175fcb2..045f3c93f717f7cb198130835d108dcb44e544c2 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -554,32 +554,74 @@ OFCondition DcmItem::writeXML(STD_NAMESPACE ostream &out,
 
 // ********************************
 
-
 OFCondition DcmItem::writeJson(STD_NAMESPACE ostream &out,
                                DcmJsonFormat &format)
 {
+    return writeJsonExt(out, format, OFTrue, OFFalse);
+}
+
+// ********************************
+
+OFCondition DcmItem::writeJsonExt(STD_NAMESPACE ostream &out,
+                               DcmJsonFormat &format,
+                                OFBool printBraces,
+                                OFBool printNewline)
+{
+    size_t num_printed = 0;
+    OFBool first = OFTrue;
+    DcmObject *elem = NULL;
+    OFCondition status = EC_Normal;
+
     if (!elementList->empty())
     {
-        // write content of all children
-        out << "{" << format.newline();
+        // iterate through all elements in this item
         elementList->seek(ELP_first);
-        OFCondition status = EC_Normal;
-        status = elementList->get()->writeJson(out, format);
-        while (status.good() && elementList->seek(ELP_next))
+        do
         {
-            out << "," << format.newline();
-            status = elementList->get()->writeJson(out, format);
+            // get next item
+            elem = elementList->get();
+
+            // check if this is a group length, and if so, ignore
+            if (elem->getTag().getElement() != 0)
+            {
+              // if this is the first element to be printed, print opening braces if needed
+              if (first && printBraces) out << "{" << format.newline();
+
+              // if this is not the first element to be printed, start with a comma
+              if (!first) out << "," << format.newline();
+
+              // print element
+              status = elem->writeJson(out, format);
+              first = OFFalse;
+              num_printed++;
+            }
+        }
+        while (status.good() && elementList->seek(ELP_next));
+
+        // print closing braces if and only if there were opening braces
+        if (num_printed > 0 && printBraces)
+        {
+            out << format.newline() << format.indent() << "}";
+            if (printNewline) out << format.newline();
         }
-        out << format.newline() << format.indent() << "}";
-        return status;
     }
-    else
+
+    // if no element was printed (item empty or only group list elements)
+    if (num_printed == 0)
     {
-        out << "{}" << format.newline();
+        if (printBraces)
+        {
+            // print empty braces if requested
+            out << "{}";
+            if (printNewline) out << format.newline();
+        }
     }
-    return EC_Normal;
+
+    return status;
+
 }
 
+
 // ********************************
 
 
@@ -1610,7 +1652,7 @@ OFCondition DcmItem::writeSignatureFormat(DcmOutputStream &outStream,
           do
           {
             dO = elementList->get();
-            if (dO->transferState() != ERW_ready)
+            if (dO->isSignable() && dO->transferState() != ERW_ready)
               errorFlag = dO->writeSignatureFormat(outStream, oxfer, enctype, wcache);
           } while (errorFlag.good() && elementList->seek(ELP_next));
         }
@@ -3447,6 +3489,11 @@ OFCondition DcmItem::putAndInsertUint8Array(const DcmTag& tag,
             } else
                 elem = new DcmPolymorphOBOW(tag);
             break;
+        case EVR_px:
+            elem = new DcmPixelData(tag);
+            if (elem != NULL)
+                elem->setVR(EVR_OB);
+            break;
         case EVR_UNKNOWN:
             /* Unknown VR, e.g. tag not found in data dictionary */
             status = EC_UnknownVR;
@@ -3538,11 +3585,16 @@ OFCondition DcmItem::putAndInsertUint16Array(const DcmTag& tag,
             if (tag == DCM_PixelData)
             {
                 elem = new DcmPixelData(tag);
-                if (elem != NULL) elem->setVR(EVR_OW);
-            }
-            else
+                if (elem != NULL)
+                    elem->setVR(EVR_OW);
+            else
                 elem = new DcmPolymorphOBOW(tag);
             break;
+        case EVR_px:
+            elem = new DcmPixelData(tag);
+            if (elem != NULL)
+                elem->setVR(EVR_OW);
+            break;
         case EVR_xs:
             /* special handling */
             elem = new DcmUnsignedShort(DcmTag(tag, EVR_US));
@@ -3858,6 +3910,9 @@ OFCondition DcmItem::putAndInsertFloat64(const DcmTag& tag,
     DcmElement *elem = NULL;
     switch(tag.getEVR())
     {
+        case EVR_DS:
+            elem = new DcmDecimalString(tag);
+            break;
         case EVR_FD:
             elem = new DcmFloatingPointDouble(tag);
             break;
@@ -4152,7 +4207,7 @@ OFCondition DcmItem::insertSequenceItem(const DcmTag &seqTag,
                     if (itemNum == -1)
                     {
                         /* insert given item before last entry */
-                        status = sequence->insert(item, count - 1, OFTrue /*before*/);
+                        status = sequence->insert(item, DCM_EndOfListIndex, OFTrue /*before*/);
                     } else {
                         /* insert given item before specified entry */
                         status = sequence->insert(item, OFstatic_cast(unsigned long, itemNum), OFTrue /*before*/);
@@ -4441,6 +4496,8 @@ OFCondition DcmItem::newDicomElement(DcmElement *&newElement,
          */
         if (newTag.getEVR() != EVR_UNKNOWN)
         {
+            DCMDATA_DEBUG("DcmItem::newDicomElement() reverted VR of element " << tag
+                << " from 'UN' to '" << newTag.getVRName() << "'");
             tag.setVR(newTag.getVR());
             evr = tag.getEVR();
             readAsUN = OFTrue;
@@ -4557,7 +4614,7 @@ OFCondition DcmItem::newDicomElement(DcmElement *&newElement,
 
         // sequences and items:
         case EVR_SQ :
-            newElement = new DcmSequenceOfItems(tag, length);
+            newElement = new DcmSequenceOfItems(tag, length, readAsUN);
             break;
         case EVR_na :
             if (tag.getXTag() == DCM_Item)
@@ -4587,6 +4644,10 @@ OFCondition DcmItem::newDicomElement(DcmElement *&newElement,
                 newElement = new DcmOtherByteOtherWord(tag, length);
             break;
 
+        case EVR_px :
+            newElement = new DcmPixelData(tag, length);
+            break;
+
         // This case should only occur if we encounter an element with an invalid
         // "Pi" VR. Make sure this does not cause problems later on
         case EVR_PixelData :
@@ -4639,7 +4700,21 @@ OFCondition DcmItem::newDicomElement(DcmElement *&newElement,
                     }
                 }
             }
-            else
+            else if (tag.isPrivate())
+            {
+                // look up VR in private data dictionary
+                DcmTag newTag(tag.getXTag(), tag.getPrivateCreator());
+                // special handling for private pixel data (compressed or uncompressed)
+                if (newTag.getEVR() == EVR_px)
+                {
+                    DCMDATA_WARN("Found private element " << tag << " with VR " << tag.getVRName()
+                        << " and undefined length, reading a pixel sequence according to data dictionary");
+                    newElement = new DcmPixelData(tag, length);
+                }
+            }
+            // no element has been created yet and no error reported
+            if ((newElement == NULL) && l_error.good())
+            {
                 if (length == DCM_UndefinedLength)
                 {
                     // The attribute is OB or OW but is encoded with undefined
@@ -4658,17 +4733,17 @@ OFCondition DcmItem::newDicomElement(DcmElement *&newElement,
                             OFCondition tempcond = EC_UndefinedLengthOBOW;
                             DCMDATA_WARN("DcmItem: Parse error in " << tag << ": " << tempcond.text());
                             newElement = new DcmSequenceOfItems(tag, length);
-                        }
-                        else
-                        {
+                        } else {
                             // bail out with an error
                             l_error = EC_UndefinedLengthOBOW;
                             DCMDATA_ERROR("DcmItem: Parse error in " << tag << ": " << l_error.text());
                         }
                     }
                 } else {
+                    // default case
                     newElement = new DcmOtherByteOtherWord(tag, length);
                 }
+            }
             break;
 
         // read unknown types as byte string:
index 9efb1b9bc1d788ebde22f40a9db58d0aa6c8ef8c..2b202640299b616ca18812df449d9b352d05e86e 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016-2017, OFFIS e.V.
+ *  Copyright (C) 2016-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -78,15 +78,21 @@ void DcmJsonFormat::escapeControlCharacters(STD_NAMESPACE ostream &out, const OF
 // Formats the number to JSON standard as DecimalString
 void DcmJsonFormat::normalizeDecimalString(OFString &value)
 {
+    // remove all plus characters that may occur in the string.
+    // These are permitted in DICOM but not in Json.
+    size_t pos;
+    while (OFString_npos != (pos = value.find('+')))
+      value.erase(pos,1);
+
     OFBool minus = OFFalse;
 
-    if (value[0] == '-')
+    if (value.length() > 0 && value[0] == '-')
     {
         value = value.substr(1);
         minus = OFTrue;
     }
 
-    size_t pos = value.find_first_not_of("0");
+    pos = value.find_first_not_of("0");
 
     if (pos == OFString_npos)
         value = "0";
@@ -105,15 +111,21 @@ void DcmJsonFormat::normalizeDecimalString(OFString &value)
 // Formats the number to JSON standard as IntegerString
 void DcmJsonFormat::normalizeIntegerString(OFString &value)
 {
+    // remove all plus characters that may occur in the string.
+    // These are permitted in DICOM but not in Json.
+    size_t pos;
+    while (OFString_npos != (pos = value.find('+')))
+      value.erase(pos,1);
+
     OFBool minus = OFFalse;
 
-    if (value[0] == '-')
+    if (value.length() > 0 && value[0] == '-')
     {
         value = value.substr(1);
         minus = OFTrue;
     }
 
-    size_t pos = value.find_first_not_of("0");
+    pos = value.find_first_not_of("0");
 
     if (pos == OFString_npos)
         value = "0";
@@ -215,7 +227,7 @@ void DcmJsonFormat::printNextArrayElementPrefix(STD_NAMESPACE ostream &out)
 // This also manipulate uri String, if BulkDataURI should be printed.
 OFBool DcmJsonFormat::asBulkDataURI(const DcmTagKey& /*tag*/, OFString& /*uri*/)
 {
-    return false;
+    return OFFalse;
 }
 
 //Class for formatted output
index d859672d58868687717ff2116b9e915cbbd52c29..3104da27264155d3f62e67c5a1615d5c32c81e25 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2010, OFFIS e.V.
+ *  Copyright (C) 1994-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -71,7 +71,7 @@ DcmList::~DcmList()
         do {
             DcmListNode *temp = firstNode;
             firstNode = firstNode->nextNode;
-            // delete temp->objNodeValue;;        // dangerous!
+            // delete temp->objNodeValue;         // dangerous!
             delete temp;
         } while ( firstNode != NULL );
         currentNode = firstNode = lastNode = NULL;
@@ -254,10 +254,23 @@ DcmObject *DcmList::seek( E_ListPos pos )
 
 DcmObject *DcmList::seek_to(unsigned long absolute_position)
 {
-    const unsigned long tmppos = absolute_position < cardinality ? absolute_position : cardinality;
-    seek( ELP_first );
-    for (unsigned long i = 0; i < tmppos; i++)
-        seek( ELP_next );
+    if (absolute_position < cardinality / 2)
+    {
+        /* iterate over first half of the list */
+        seek( ELP_first );
+        for (unsigned long i = 0; i < absolute_position; i++)
+            seek( ELP_next );
+    }
+    else if (absolute_position < cardinality)
+    {
+        /* iterate over second half of the list (starting from the end) */
+        seek( ELP_last );
+        for (unsigned long i = absolute_position + 1; i < cardinality; i++)
+            seek( ELP_prev );
+    } else {
+        /* invalid position */
+        currentNode = NULL;
+    }
     return get( ELP_atpos );
 }
 
index 68b687849cb3aaa66e7b863edb2d817d175072db..8bef02b5933b8228911aee3e8139712260c18c2d 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -380,8 +380,12 @@ OFCondition DcmMetaInfo::readGroupLength(DcmInputStream &inStream,
                 l_error = (OFstatic_cast(DcmUnsignedLong *, elementList->get()))->getUint32(headerLen);
                 DCMDATA_TRACE("DcmMetaInfo::readGroupLength() Group Length of File Meta Header = " << headerLen + bytesRead);
             } else {
-                l_error = EC_CorruptedData;
                 DCMDATA_WARN("DcmMetaInfo: No Group Length available in Meta Information Header");
+                /* missing group length could be ignored (if no other error occurred) */
+                if (l_error == EC_StreamNotifyClient)
+                    l_error = EC_InvalidStream;
+                else if (l_error != EC_InvalidStream)
+                    l_error = EC_CorruptedData;
             }
         }
     }
index 8d1d2ad457432285d2a03e6b6c7c4de2835252b9..13f4baebe2b9a93eff88cfc4594e9f0283222518 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -464,18 +464,18 @@ Uint32 DcmObject::getTagAndLengthSize(const E_TransferSyntax oxfer) const
 
     if (oxferSyn.isExplicitVR())
     {
-       /* map "UN" to "OB" if generation of "UN" is disabled */
-       DcmVR outvr(getTag().getVR().getValidEVR());
-
-       if (Length > 0xffff || outvr.usesExtendedLengthEncoding())
-       {
-         // we are either using extended length encoding or the
-         // element length is > 64k (i.e. we have to convert to OB/UN).
-         // In any case we need a 12-byte header field.
-         // This is also the case for any object with undefined length,
-         // so we don't need to check that as a special case.
-          return 12;
-       }
+        /* map "UN" to "OB" if generation of "UN" is disabled */
+        DcmVR outvr(getTag().getVR().getValidEVR());
+
+        if (Length > 0xffff || outvr.usesExtendedLengthEncoding())
+        {
+            /* We are either using extended length encoding or the */
+            /* element length is > 64k (i.e. we have to convert to OB/UN). */
+            /* In any case we need a 12-byte header field. */
+            /* This is also the case for any object with undefined length, */
+            /* so we don't need to check that as a special case. */
+            return 12;
+        }
     }
     return 8;
 }
@@ -535,10 +535,13 @@ OFCondition DcmObject::writeTagAndLength(DcmOutputStream &outStream,
 
             if (Length > 0xffff && (!myvr.usesExtendedLengthEncoding()))
             {
-              // Attribute length is larger than 64 kBytes.
-              // We need to encode this as UN (or OB, if generation of UN is disabled
-              if (dcmEnableUnknownVRGeneration.get()) vr = EVR_UN; else vr = EVR_OB;
-              myvr.setVR(vr);
+                /* Attribute length is larger than 64 kBytes. */
+                /* We need to encode this as UN (or OB, if generation of UN is disabled */
+                if (dcmEnableUnknownVRGeneration.get()) vr = EVR_UN; else vr = EVR_OB;
+                myvr.setVR(vr);
+                /* output debug information to the logger */
+                DCMDATA_DEBUG("DcmObject::writeTagAndLength() Length of element " << Tag
+                    << " exceeds maximum of 16-bit length field, changing VR to " << myvr.getVRName());
             }
 
             /* get name of data type */
index ae8acfc775bc0d4a3625c5d4211120359d944d23..6d97682e69a124e2de807678fcc585f7364f8b0b 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2008-2018, OFFIS e.V.
+ *  Copyright (C) 2008-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -20,7 +20,7 @@
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 
 #include "dcmtk/dcmdata/dcpath.h"
 #include "dcmtk/dcmdata/dcsequen.h"
 #define INCLUDE_CINTTYPES
 #include "dcmtk/ofstd/ofstdinc.h"
 
-
 /*******************************************************************/
 /*              Implementation of class DcmPath                    */
 /*******************************************************************/
 
 // Constructor
-DcmPath::DcmPath() :
-  m_path()
+DcmPath::DcmPath()
+    : m_path()
 {
 }
 
-
 // Construct from existing path (kind of copy constructor)
-DcmPath::DcmPath(const OFList<DcmPathNode*>& currentPath) :
-  m_path()
+DcmPath::DcmPath(const OFList<DcmPathNode*>& currentPath)
+    : m_path()
 {
-  OFListConstIterator(DcmPathNode*) it = currentPath.begin();
-  OFListConstIterator(DcmPathNode*) endOfPath = currentPath.end();
-  while (it != endOfPath)
-  {
-    m_path.push_back(new DcmPathNode( (*it)->m_obj, (*it)->m_itemNo ));
-    it++;
-  }
+    OFListConstIterator(DcmPathNode*) it        = currentPath.begin();
+    OFListConstIterator(DcmPathNode*) endOfPath = currentPath.end();
+    while (it != endOfPath)
+    {
+        m_path.push_back(new DcmPathNode((*it)->m_obj, (*it)->m_itemNo));
+        it++;
+    }
 }
 
-
 // Append a node to the path
 void DcmPath::append(DcmPathNode* node)
 {
-  if (node != NULL)
-    m_path.push_back(node); // do any validity checking?
+    if (node != NULL)
+        m_path.push_back(node); // do any validity checking?
 }
 
-
 // Deletes last node from the path and frees corresponding memory
 void DcmPath::deleteBackNode()
 {
-  DcmPathNode* node = m_path.back();
-  m_path.pop_back();
-  if (node)
-  {
-    delete node; node = NULL;
-  }
+    DcmPathNode* node = m_path.back();
+    m_path.pop_back();
+    if (node)
+    {
+        delete node;
+        node = NULL;
+    }
 }
 
-
 // Returns iterator to first element of the path
 OFListIterator(DcmPathNode*) DcmPath::begin()
 {
-  return m_path.begin();
+    return m_path.begin();
 }
 
-
 // Returns iterator to last element of the path
 DcmPathNode* DcmPath::back()
 {
-  return m_path.back();
+    return m_path.back();
 }
 
 // Returns iterator to the end of path, i.e. dummy after actual last element
 OFListIterator(DcmPathNode*) DcmPath::end()
 {
-  return m_path.end();
+    return m_path.end();
 }
 
-
 // Returns number of path nodes in the path
 Uint32 DcmPath::size() const
 {
-  return OFstatic_cast(Uint32, m_path.size());
+    return OFstatic_cast(Uint32, m_path.size());
 }
 
-
 // Returns true if path is empty, i.e. number of path nodes is zero
 OFBool DcmPath::empty() const
 {
-  return (m_path.size() == 0);
+    return (m_path.size() == 0);
 }
 
-
 // Returns string representation of the path
 OFString DcmPath::toString() const
 {
-  OFListConstIterator(DcmPathNode*) it = m_path.begin();
-  OFListConstIterator(DcmPathNode*) endOfList = m_path.end();
-  OFString pathStr; DcmEVR vr; DcmObject* obj;
-  char buf[500];
-  while (it != endOfList)
-  {
-    if ( ((*it) == NULL) || ((*it)->m_obj == NULL) )
-      return "Invalid search result";
-    obj = (*it)->m_obj;
-    vr = obj->ident();
-    if ((vr == EVR_SQ) || ( obj->isLeaf()) )
-    {
-      pathStr.append( OFconst_cast(DcmTag*, &obj->getTag())->getTagName() );
-      it++;
-    }
-    else if ( (vr == EVR_item) || (vr == EVR_dataset) )
+    OFListConstIterator(DcmPathNode*) it        = m_path.begin();
+    OFListConstIterator(DcmPathNode*) endOfList = m_path.end();
+    OFString pathStr;
+    DcmEVR vr;
+    DcmObject* obj;
+    char buf[500];
+    while (it != endOfList)
     {
+        if (((*it) == NULL) || ((*it)->m_obj == NULL))
+            return "Invalid search result";
+        obj = (*it)->m_obj;
+        vr  = obj->ident();
+        if ((vr == EVR_SQ) || (obj->isLeaf()))
+        {
+            pathStr.append(OFconst_cast(DcmTag*, &obj->getTag())->getTagName());
+            it++;
+        }
+        else if ((vr == EVR_item) || (vr == EVR_dataset))
+        {
 #ifdef PRIu32
-      sprintf(buf, "[%" PRIu32 "]", (*it)->m_itemNo);
+            sprintf(buf, "[%" PRIu32 "]", (*it)->m_itemNo);
 #elif SIZEOF_LONG == 8
-      sprintf(buf, "[%u]", (*it)->m_itemNo);
+            sprintf(buf, "[%u]", (*it)->m_itemNo);
 #else
-      sprintf(buf, "[%lu]", (*it)->m_itemNo);
+            sprintf(buf, "[%lu]", (*it)->m_itemNo);
 #endif
-      pathStr.append(buf);
-      it++;
-      if (it != endOfList) pathStr.append(".");
-    }
-    else
-    {
-      pathStr.append("<UNKNOWN>");
-      it++;
+            pathStr.append(buf);
+            it++;
+            if (it != endOfList)
+                pathStr.append(".");
+        }
+        else
+        {
+            pathStr.append("<UNKNOWN>");
+            it++;
+        }
     }
-  }
-  return pathStr;
+    return pathStr;
 }
 
-
 // Checks whether a specific group number is used in the path's path nodes
 OFBool DcmPath::containsGroup(const Uint16 groupNo) const
 {
-  OFListConstIterator(DcmPathNode*) it = m_path.begin();
-  OFListConstIterator(DcmPathNode*) endOfList = m_path.end();
-  while (it != endOfList)
-  {
-    DcmPathNode* node = *it;
-    if ( (node == NULL) || (node->m_obj == NULL) ) return OFFalse;
-    if (node->m_obj->getGTag() == groupNo) return OFTrue;
-    it++;
-  }
-  return OFFalse;
+    OFListConstIterator(DcmPathNode*) it        = m_path.begin();
+    OFListConstIterator(DcmPathNode*) endOfList = m_path.end();
+    while (it != endOfList)
+    {
+        DcmPathNode* node = *it;
+        if ((node == NULL) || (node->m_obj == NULL))
+            return OFFalse;
+        if (node->m_obj->getGTag() == groupNo)
+            return OFTrue;
+        it++;
+    }
+    return OFFalse;
 }
 
-
 // Helper function for findOrCreatePath(). Parses item no from start of string
-OFCondition DcmPath::parseItemNoFromPath(OFString& path,        // inout
-                                         Uint32& itemNo,        // out
-                                         OFBool& wasWildcard)   // out
+OFCondition DcmPath::parseItemNoFromPath(OFString& path,      // inout
+                                         Uint32& itemNo,      // out
+                                         OFBool& wasWildcard) // out
 {
-  wasWildcard = OFFalse;
-  itemNo = 0;
-  // check whether there is an item to parse
-  size_t closePos = path.find_first_of(']', 0);
-  if ( (closePos != OFString_npos) && (path[0] == '[') )
-  {
-    long int parsedNo;
-    // try parsing item number; parsing for %lu would cause overflows in case of negative numbers
-    int parsed = sscanf(path.c_str(), "[%ld]", &parsedNo);
-    if (parsed == 1)
-    {
-      if (parsedNo < 0)
-      {
-        OFString errMsg = "Negative item number (not permitted) at beginning of path: "; errMsg += path;
-        return makeOFCondition(OFM_dcmdata, 25, OF_error, errMsg.c_str());
-      }
-      itemNo = OFstatic_cast(Uint32, parsedNo);
-      if (closePos + 1 < path.length()) // if end of path not reached, cut off "."
-        closePos ++;
-      path.erase(0, closePos + 1); // remove item from path
-      return EC_Normal;
-    }
-    char aChar;
-    parsed = sscanf(path.c_str(), "[%c]", &aChar);
-    if ( (parsed == 1) && (aChar =='*') )
-    {
-      wasWildcard = OFTrue;
-      if (closePos + 1 < path.length()) // if end of path not reached, cut off "."
-        closePos ++;
-      path.erase(0, closePos + 1); // remove item from path
-      return EC_Normal;
-    }
-  }
-  OFString errMsg = "Unable to parse item number at beginning of path: "; errMsg += path;
-  return makeOFCondition(OFM_dcmdata, 25, OF_error, errMsg.c_str());
+    wasWildcard = OFFalse;
+    itemNo      = 0;
+    // check whether there is an item to parse
+    size_t closePos = path.find_first_of(']', 0);
+    if ((closePos != OFString_npos) && (path[0] == '['))
+    {
+        long int parsedNo;
+        // try parsing item number; parsing for %lu would cause overflows in case of negative numbers
+        int parsed = sscanf(path.c_str(), "[%ld]", &parsedNo);
+        if (parsed == 1)
+        {
+            if (parsedNo < 0)
+            {
+                OFString errMsg = "Negative item number (not permitted) at beginning of path: ";
+                errMsg += path;
+                return makeOFCondition(OFM_dcmdata, 25, OF_error, errMsg.c_str());
+            }
+            itemNo = OFstatic_cast(Uint32, parsedNo);
+            if (closePos + 1 < path.length()) // if end of path not reached, cut off "."
+                closePos++;
+            path.erase(0, closePos + 1); // remove item from path
+            return EC_Normal;
+        }
+        char aChar;
+        parsed = sscanf(path.c_str(), "[%c]", &aChar);
+        if ((parsed == 1) && (aChar == '*'))
+        {
+            wasWildcard = OFTrue;
+            if (closePos + 1 < path.length()) // if end of path not reached, cut off "."
+                closePos++;
+            path.erase(0, closePos + 1); // remove item from path
+            return EC_Normal;
+        }
+    }
+    OFString errMsg = "Unable to parse item number at beginning of path: ";
+    errMsg += path;
+    return makeOFCondition(OFM_dcmdata, 25, OF_error, errMsg.c_str());
 }
 
-
 // Function that parses a tag from the beginning of a path string.
-OFCondition DcmPath::parseTagFromPath(OFString& path,           // inout
-                                      DcmTag& tag)              // out
+OFCondition DcmPath::parseTagFromPath(OFString& path, // inout
+                                      DcmTag& tag)    // out
 {
-  OFCondition result;
-  size_t pos = OFString_npos;
+    OFCondition result;
+    size_t pos = OFString_npos;
 
-  // In case we have a tag "(gggg,xxxx)"
-  if ( path[0] == '(')
-  {
-    pos = path.find_first_of(')', 0);
-    if (pos != OFString_npos)
-      result = DcmTag::findTagFromName(path.substr(1, pos - 1).c_str() /* "gggg,eeee" */, tag);
+    // In case we have a tag "(gggg,xxxx)"
+    if (path[0] == '(')
+    {
+        pos = path.find_first_of(')', 0);
+        if (pos != OFString_npos)
+            result = DcmTag::findTagFromName(path.substr(1, pos - 1).c_str() /* "gggg,eeee" */, tag);
+        else
+        {
+            OFString errMsg("Unable to parse tag at beginning of path: ");
+            errMsg += path;
+            return makeOFCondition(OFM_dcmdata, 25, OF_error, errMsg.c_str());
+        }
+        pos++; // also cut off closing bracket
+    }
+    // otherwise we could have a dictionary name
     else
     {
-      OFString errMsg("Unable to parse tag at beginning of path: "); errMsg += path;
-      return makeOFCondition(OFM_dcmdata, 25, OF_error, errMsg.c_str());
-    }
-    pos++; // also cut off closing bracket
-  }
-  // otherwise we could have a dictionary name
-  else
-  {
-    // maybe an item follows
-    pos = path.find_first_of('[', 0);
-    if (pos == OFString_npos)
-      result = DcmTag::findTagFromName(path.c_str(), tag); // check full path
+        // maybe an item follows
+        pos = path.find_first_of('[', 0);
+        if (pos == OFString_npos)
+            result = DcmTag::findTagFromName(path.c_str(), tag); // check full path
+        else
+            result = DcmTag::findTagFromName(path.substr(0, pos).c_str(), tag); // parse path up to "[" char
+    }
+    // construct error message if necessary and return
+    if (result.bad())
+    {
+        OFString errMsg("Unable to parse tag/dictionary name at beginning of path: ");
+        errMsg += path;
+        return makeOFCondition(OFM_dcmdata, 25, OF_error, errMsg.c_str());
+    }
+    // else remove parsed tag from path and return success
     else
-      result = DcmTag::findTagFromName(path.substr(0, pos).c_str(), tag); // parse path up to "[" char
-  }
-  // construct error message if necessary and return
-  if (result.bad())
-  {
-    OFString errMsg("Unable to parse tag/dictionary name at beginning of path: "); errMsg += path;
-    return makeOFCondition(OFM_dcmdata, 25, OF_error, errMsg.c_str());
-  }
-  // else remove parsed tag from path and return success
-  else
-    path.erase(0, pos);
-  return EC_Normal;
-}
+    {
+        path.erase(0, pos);
+    }
 
+    return EC_Normal;
+}
 
 // Destructor, frees memory of path nodes (but not of underlying DICOM objects)
 DcmPath::~DcmPath()
 {
-  // free dynamically allocated memory
-  while (m_path.size() != 0)
-  {
-    DcmPathNode* node = m_path.front();
-    delete node; node = NULL;
-    m_path.pop_front();
-  }
+    // free dynamically allocated memory
+    while (m_path.size() != 0)
+    {
+        DcmPathNode* node = m_path.front();
+        delete node;
+        node = NULL;
+        m_path.pop_front();
+    }
 }
 
-
 // Separate a string path into the different nodes
-OFCondition DcmPath::separatePathNodes(const OFString& path,
-                                       OFList<OFString>& result)
+OFCondition DcmPath::separatePathNodes(const OFString& path, OFList<OFString>& result)
 {
-  OFString pathStr(path);
-  OFCondition status = EC_Normal;
-  OFBool nextIsItem = OFTrue;
-  Uint32 itemNo = 0;
-  OFBool isWildcard = OFFalse;
-
-  // initialize parsing loop
-  if (!pathStr.empty())
-  {
-    if (pathStr[0] != '[')
-      nextIsItem = OFFalse;
-  }
-
-  char buf[100];
-  // parse node for node and only stop if error occurs or parsing completes
-  while ( !pathStr.empty() )
-  {
-    if (nextIsItem)
-    {
-      status = parseItemNoFromPath(pathStr, itemNo, isWildcard);
-      if (status.bad()) return status;
-      if (isWildcard)
-        result.push_back("[*]");
-      else
-      {
+    OFString pathStr(path);
+    OFCondition status = EC_Normal;
+    OFBool nextIsItem  = OFTrue;
+    Uint32 itemNo      = 0;
+    OFBool isWildcard  = OFFalse;
+
+    // initialize parsing loop
+    if (!pathStr.empty())
+    {
+        if (pathStr[0] != '[')
+            nextIsItem = OFFalse;
+    }
+
+    char buf[100];
+    // parse node for node and only stop if error occurs or parsing completes
+    while (!pathStr.empty())
+    {
+        if (nextIsItem)
+        {
+            status = parseItemNoFromPath(pathStr, itemNo, isWildcard);
+            if (status.bad())
+                return status;
+            if (isWildcard)
+                result.push_back("[*]");
+            else
+            {
 #ifdef PRIu32
-        if (sprintf(buf, "[%" PRIu32 "]", itemNo) < 2) return EC_IllegalParameter;
+                if (sprintf(buf, "[%" PRIu32 "]", itemNo) < 2)
+                    return EC_IllegalParameter;
 #elif SIZEOF_LONG == 8
-        if (sprintf(buf, "[%u]", itemNo) < 2) return EC_IllegalParameter;
+                if (sprintf(buf, "[%u]", itemNo) < 2)
+                    return EC_IllegalParameter;
 #else
-        if (sprintf(buf, "[%lu]", itemNo) < 2) return EC_IllegalParameter;
+                if (sprintf(buf, "[%lu]", itemNo) < 2)
+                    return EC_IllegalParameter;
 #endif
-        result.push_back(buf);
-      }
-      nextIsItem = OFFalse;
-    }
-    else
-    {
-      DcmTag tag;
-      status = parseTagFromPath(pathStr, tag);
-      if (status.bad())
-        return status;
-      if (sprintf(buf, "(%04X,%04X)", tag.getGroup(), tag.getElement()) != 11)
-        return EC_IllegalParameter;
-      result.push_back(buf);
-      nextIsItem = OFTrue;
+                result.push_back(buf);
+            }
+            nextIsItem = OFFalse;
+        }
+        else
+        {
+            DcmTag tag;
+            status = parseTagFromPath(pathStr, tag);
+            if (status.bad())
+                return status;
+            if (sprintf(buf, "(%04X,%04X)", tag.getGroup(), tag.getElement()) != 11)
+                return EC_IllegalParameter;
+            result.push_back(buf);
+            nextIsItem = OFTrue;
+        }
     }
-  }
-  return status;
+    return status;
 }
 
-
 /*******************************************************************/
 /*          Implementation of class DcmPathProcessor               */
 /*******************************************************************/
 
-
 // Constructor, constructs an empty path processor
-DcmPathProcessor::DcmPathProcessor() :
-  m_currentPath(),
-  m_results(),
-  m_createIfNecessary(OFFalse),
-  m_checkPrivateReservations(OFTrue),
-  m_itemWildcardsEnabled(OFTrue)
+DcmPathProcessor::DcmPathProcessor()
+    : m_currentPath()
+    , m_results()
+    , m_createIfNecessary(OFFalse)
+    , m_checkPrivateReservations(OFTrue)
+    , m_itemWildcardsEnabled(OFTrue)
 {
 }
 
-
 // enables (class default:enabled) or disables checking of private reservations
 void DcmPathProcessor::checkPrivateReservations(const OFBool doChecking)
 {
-  m_checkPrivateReservations = doChecking;
+    m_checkPrivateReservations = doChecking;
 }
 
-
 // enables (class default:enabled) or disables support for item wildcards
 void DcmPathProcessor::setItemWildcardSupport(const OFBool supported)
 {
-  m_itemWildcardsEnabled = supported;
+    m_itemWildcardsEnabled = supported;
 }
 
-
 // Permits finding and creating DICOM object hierarchies based on a path string
-OFCondition DcmPathProcessor::findOrCreatePath(DcmObject* obj,
-                                               const OFString& path,
-                                               OFBool createIfNecessary)
+OFCondition DcmPathProcessor::findOrCreatePath(DcmObject* obj, const OFString& path, OFBool createIfNecessary)
 {
-  // check input parameters
-  if ( (obj == NULL) || path.empty())
-    return EC_IllegalParameter;
-
-  if (!m_itemWildcardsEnabled)
-  {
-    if (path.find('*') != OFString_npos)
-    {
-      return makeOFCondition(OFM_dcmdata, 25, OF_error, "Item wildcard '*' found in path but wildcards disabled");
-    }
-  }
-  clear();
-  m_createIfNecessary = createIfNecessary;
-
-  // do real work in private member functions
-  OFString pathCopy = path;
-  if ((obj->ident() == EVR_item) || (obj->ident() == EVR_dataset))
-    return findOrCreateItemPath(OFstatic_cast(DcmItem*, obj), pathCopy);
-  else if (obj->ident() == EVR_SQ)
-    return findOrCreateSequencePath(OFstatic_cast(DcmSequenceOfItems*, obj), pathCopy);
-  else
-    return EC_IllegalParameter;
-}
+    // check input parameters
+    if ((obj == NULL) || path.empty())
+        return EC_IllegalParameter;
 
+    if (!m_itemWildcardsEnabled)
+    {
+        if (path.find('*') != OFString_npos)
+        {
+            return makeOFCondition(OFM_dcmdata, 25, OF_error, "Item wildcard '*' found in path but wildcards disabled");
+        }
+    }
+    clear();
+    m_createIfNecessary = createIfNecessary;
+
+    // do real work in private member functions
+    OFString pathCopy = path;
+    if ((obj->ident() == EVR_item) || (obj->ident() == EVR_dataset))
+        return findOrCreateItemPath(OFstatic_cast(DcmItem*, obj), pathCopy);
+    else if (obj->ident() == EVR_SQ)
+        return findOrCreateSequencePath(OFstatic_cast(DcmSequenceOfItems*, obj), pathCopy);
+    else
+        return EC_IllegalParameter;
+}
 
 // Permits deleting DICOM object hierarchies based on a path string
-OFCondition DcmPathProcessor::findOrDeletePath(DcmObject* obj,
-                                               const OFString& path,
-                                               Uint32& numDeleted)
+OFCondition DcmPathProcessor::findOrDeletePath(DcmObject* obj, const OFString& path, Uint32& numDeleted)
 {
-  // check input parameters
-  if ( (obj == NULL) || path.empty())
-    return EC_IllegalParameter;
-  numDeleted = 0;
-  if (!m_itemWildcardsEnabled)
-  {
-    if (path.find('*') != OFString_npos)
-    {
-      return makeOFCondition(OFM_dcmdata, 25, OF_error, "Item wildcard '*' found in path but wildcards disabled");
-    }
-  }
-
-  // search
-  m_createIfNecessary = OFFalse;
-  OFString pathCopy = path;
-  OFCondition result;
-  clear();
-  if ((obj->ident() == EVR_item) || (obj->ident() == EVR_dataset))
-    result = findOrCreateItemPath(OFstatic_cast(DcmItem*, obj), pathCopy);
-  else if (obj->ident() == EVR_SQ)
-    result = findOrCreateSequencePath(OFstatic_cast(DcmSequenceOfItems*, obj), pathCopy);
-  else
-    return EC_IllegalParameter;
-  if (result.bad()) return result;
-
-  // check results
-  OFList<DcmPath*> resultPaths;
-  Uint32 numPaths = getResults(resultPaths);
-  if (numPaths == 0) return EC_IllegalCall; // should never happen at this point
-  OFListIterator(DcmPath*) pathIt = resultPaths.begin();
-  OFListIterator(DcmPath*) endIt = resultPaths.end();
-  while (pathIt != endIt)
-  {
-    // get last item/element from path which should be deleted
-    DcmPathNode* nodeToDelete = (*pathIt)->back();
-    if ( (nodeToDelete == NULL) || (nodeToDelete->m_obj == NULL) ) return EC_IllegalCall;
-
-    // if it's not an item, delete element from item.
-    // deletes DICOM content of node but not node itself (done later)
-    if (nodeToDelete->m_obj->ident() != EVR_item)
-    {
-      result = deleteLastElemFromPath(obj, *pathIt, nodeToDelete);
-    }
-    // otherwise we need to delete an item from a sequence
+    // check input parameters
+    if ((obj == NULL) || path.empty())
+        return EC_IllegalParameter;
+    numDeleted = 0;
+    if (!m_itemWildcardsEnabled)
+    {
+        if (path.find('*') != OFString_npos)
+        {
+            return makeOFCondition(OFM_dcmdata, 25, OF_error, "Item wildcard '*' found in path but wildcards disabled");
+        }
+    }
+
+    // search
+    m_createIfNecessary = OFFalse;
+    OFString pathCopy   = path;
+    OFCondition result;
+    clear();
+    if ((obj->ident() == EVR_item) || (obj->ident() == EVR_dataset))
+        result = findOrCreateItemPath(OFstatic_cast(DcmItem*, obj), pathCopy);
+    else if (obj->ident() == EVR_SQ)
+        result = findOrCreateSequencePath(OFstatic_cast(DcmSequenceOfItems*, obj), pathCopy);
     else
+        return EC_IllegalParameter;
+    if (result.bad())
+        return result;
+
+    // check results
+    OFList<DcmPath*> resultPaths;
+    Uint32 numPaths = getResults(resultPaths);
+    if (numPaths == 0)
+        return EC_IllegalCall; // should never happen at this point
+    OFListIterator(DcmPath*) pathIt = resultPaths.begin();
+    OFListIterator(DcmPath*) endIt  = resultPaths.end();
+    while (pathIt != endIt)
     {
-      result = deleteLastItemFromPath(obj, *pathIt, nodeToDelete);
+        // get last item/element from path which should be deleted
+        DcmPathNode* nodeToDelete = (*pathIt)->back();
+        if ((nodeToDelete == NULL) || (nodeToDelete->m_obj == NULL))
+            return EC_IllegalCall;
+
+        // if it's not an item, delete element from item.
+        // deletes DICOM content of node but not node itself (done later)
+        if (nodeToDelete->m_obj->ident() != EVR_item)
+        {
+            result = deleteLastElemFromPath(obj, *pathIt, nodeToDelete);
+        }
+        // otherwise we need to delete an item from a sequence
+        else
+        {
+            result = deleteLastItemFromPath(obj, *pathIt, nodeToDelete);
+        }
+        if (result.bad())
+            return result;
+        // if success, remove node from path and clear node memory
+        (*pathIt)->deleteBackNode();
+        numDeleted++;
+        pathIt++;
     }
-    if (result.bad()) return result;
-    // if success, remove node from path and clear node memory
-    (*pathIt)->deleteBackNode();
-    numDeleted++;
-    pathIt++;
-  }
-  return result;
+    return result;
 }
 
-
 // Get results of a an operation started before (e.g. findOrCreatePath())
 Uint32 DcmPathProcessor::getResults(OFList<DcmPath*>& searchResults)
 {
-  if (m_results.size() > 0)
-  {
-    // explicitly copy (shallow)
-    OFListIterator(DcmPath*) it = m_results.begin();
-    while (it != m_results.end())
+    if (m_results.size() > 0)
     {
-      searchResults.push_back(*it);
-      it++;
+        // explicitly copy (shallow)
+        OFListIterator(DcmPath*) it = m_results.begin();
+        while (it != m_results.end())
+        {
+            searchResults.push_back(*it);
+            it++;
+        }
     }
-  }
-  return OFstatic_cast(Uint32, m_results.size());
+    return OFstatic_cast(Uint32, m_results.size());
 }
 
 // applies a string path (optionally with value) to a dataset
-OFCondition DcmPathProcessor::applyPathWithValue(DcmDataset* dataset,
-                                                 const OFString& overrideKey)
+OFCondition DcmPathProcessor::applyPathWithValue(DcmDataset* dataset, const OFString& overrideKey)
 {
-  if (dataset == NULL) return EC_IllegalCall;
-  if (overrideKey.empty()) return EC_Normal;
-  OFString path = overrideKey;
-  OFString value;
-  size_t pos = path.find('=');
-  // separate tag from value if there is one
-  if (pos != OFString_npos)
-  {
-    value = path.substr(pos + 1); // value now contains value
-    path.erase(pos);              // pure path without value
-  }
-  clear();
-
-  // create path
-  OFCondition result = findOrCreatePath(dataset, path, OFTrue /* create if necessary */);
-  if (result.bad())
-    return result;
+    if (dataset == NULL)
+        return EC_IllegalCall;
+    if (overrideKey.empty())
+        return EC_Normal;
+    OFString path = overrideKey;
+    OFString value;
+    size_t pos = path.find('=');
+    // separate tag from value if there is one
+    if (pos != OFString_npos)
+    {
+        value = path.substr(pos + 1); // value now contains value
+        path.erase(pos);              // pure path without value
+    }
+    clear();
 
-  // prepare for value insertion
-  OFListConstIterator(DcmPath*) it = m_results.begin();
-  OFListConstIterator(DcmPath*) endList = m_results.end();
-  DcmPathNode* last = (*it)->back();
-  if (last == NULL) return EC_IllegalCall;
-  // if value is specified, be sure path does not end with item
-  if ( !last->m_obj->isLeaf() )
-  {
-    if (value.empty())
-      return EC_Normal;
-    else
-      return makeOFCondition(OFM_dcmdata, 25, OF_error, "Cannot insert value into path ending with item or sequence");
-  }
-  // insert value into each element affected by path
-  while (it != endList)
-  {
-    last = (*it)->back();
-    if (last == NULL) return EC_IllegalCall;
-    DcmElement* elem = OFstatic_cast(DcmElement*, last->m_obj);
-    if (elem == NULL) return EC_IllegalCall;
-    result = elem->putString(value.c_str());
+    // create path
+    OFCondition result = findOrCreatePath(dataset, path, OFTrue /* create if necessary */);
     if (result.bad())
-      break;
-    it++;
-  }
-  return result;
-}
+        return result;
 
+    // prepare for value insertion
+    OFListConstIterator(DcmPath*) it      = m_results.begin();
+    OFListConstIterator(DcmPath*) endList = m_results.end();
+    DcmPathNode* last                     = (*it)->back();
+    if (last == NULL)
+        return EC_IllegalCall;
+    // if value is specified, be sure path does not end with item
+    if (!last->m_obj->isLeaf())
+    {
+        if (value.empty())
+            return EC_Normal;
+        else
+            return makeOFCondition(
+                OFM_dcmdata, 25, OF_error, "Cannot insert value into path ending with item or sequence");
+    }
+    // insert value into each element affected by path
+    while (it != endList)
+    {
+        last = (*it)->back();
+        if (last == NULL)
+            return EC_IllegalCall;
+        DcmElement* elem = OFstatic_cast(DcmElement*, last->m_obj);
+        if (elem == NULL)
+            return EC_IllegalCall;
+        result = elem->putString(value.c_str());
+        if (result.bad())
+            break;
+        it++;
+    }
+    return result;
+}
 
 // Resets status (including results) of DcmPathProcessor and frees corresponding memory
 void DcmPathProcessor::clear()
 {
-  while (m_results.size() != 0)
-  {
-    DcmPath* result = m_results.front();
-    if (result != NULL)
+    while (m_results.size() != 0)
     {
-      delete result;
-      result = NULL;
+        DcmPath* result = m_results.front();
+        if (result != NULL)
+        {
+            delete result;
+            result = NULL;
+        }
+        m_results.pop_front();
     }
-    m_results.pop_front();
-  }
 
-  while (m_currentPath.size() != 0)
-  {
-    DcmPathNode* node = m_currentPath.front();
-    if (node != NULL)
+    while (m_currentPath.size() != 0)
     {
-      delete node;
-      node = NULL;
+        DcmPathNode* node = m_currentPath.front();
+        if (node != NULL)
+        {
+            delete node;
+            node = NULL;
+        }
+        m_currentPath.pop_front();
     }
-    m_currentPath.pop_front();
-  }
-
 }
 
-
 // Destructor, frees memory by calling clear()
 DcmPathProcessor::~DcmPathProcessor()
 {
-  clear();
+    clear();
 }
 
-
 /* protected helper functions */
 
 // Helper function that deletes last DICOM element from a path from the DICOM hierarchy
-OFCondition DcmPathProcessor::deleteLastElemFromPath(DcmObject* objSearchedIn,
-                                                     DcmPath* path,
-                                                     DcmPathNode* toDelete)
+OFCondition DcmPathProcessor::deleteLastElemFromPath(DcmObject* objSearchedIn, DcmPath* path, DcmPathNode* toDelete)
 {
-  // item containing the element to delete
-  DcmItem* containingItem = NULL;
-  if ( path->size() == 1)
-  {
-    // if we have only a single elem in path, given object must be cont. item
-    if ( (objSearchedIn->ident() != EVR_item) && (objSearchedIn->ident() != EVR_dataset) )
-      return makeOFCondition(OFM_dcmdata, 25, OF_error, "Cannot search leaf element in object being not an item");
-    containingItem = OFstatic_cast(DcmItem*, objSearchedIn);
-  }
-  else
-  {
-    // get containing item from path which is the penultimate in the path
-    OFListIterator(DcmPathNode*) temp = path->end();
-    temp--; temp--;
-    if (*temp == NULL) return EC_IllegalCall; // never happens here...
-    if ( (*temp)->m_obj == NULL ) return EC_IllegalCall;
-    if ( (*temp)->m_obj->ident() != EVR_item) // (no test for dataset needed)
-      return makeOFCondition(OFM_dcmdata, 25, OF_error, "Cannot search leaf element in object being not an item");
-    containingItem = OFstatic_cast(DcmItem*, (*temp)->m_obj);
-  }
-  if (containingItem == NULL) return EC_IllegalCall;
-  OFCondition result = containingItem->findAndDeleteElement(toDelete->m_obj->getTag(), OFFalse, OFFalse);
-  return result;
+    // item containing the element to delete
+    DcmItem* containingItem = NULL;
+    if (path->size() == 1)
+    {
+        // if we have only a single elem in path, given object must be cont. item
+        if ((objSearchedIn->ident() != EVR_item) && (objSearchedIn->ident() != EVR_dataset))
+            return makeOFCondition(OFM_dcmdata, 25, OF_error, "Cannot search leaf element in object being not an item");
+        containingItem = OFstatic_cast(DcmItem*, objSearchedIn);
+    }
+    else
+    {
+        // get containing item from path which is the penultimate in the path
+        OFListIterator(DcmPathNode*) temp = path->end();
+        temp--;
+        temp--;
+        if (*temp == NULL)
+            return EC_IllegalCall; // never happens here...
+        if ((*temp)->m_obj == NULL)
+            return EC_IllegalCall;
+        if ((*temp)->m_obj->ident() != EVR_item) // (no test for dataset needed)
+            return makeOFCondition(OFM_dcmdata, 25, OF_error, "Cannot search leaf element in object being not an item");
+        containingItem = OFstatic_cast(DcmItem*, (*temp)->m_obj);
+    }
+    if (containingItem == NULL)
+        return EC_IllegalCall;
+    OFCondition result = containingItem->findAndDeleteElement(toDelete->m_obj->getTag(), OFFalse, OFFalse);
+    return result;
 }
 
-
 // Helper function that deletes last DICOM item from a path from the DICOM hierarchy
-OFCondition DcmPathProcessor::deleteLastItemFromPath(DcmObject* objSearchedIn,
-                                                     DcmPath* path,
-                                                     DcmPathNode* toDelete)
+OFCondition DcmPathProcessor::deleteLastItemFromPath(DcmObject* objSearchedIn, DcmPath* path, DcmPathNode* toDelete)
 {
-  DcmSequenceOfItems* containingSeq = NULL;
-  if ( path->size() == 1)
-  {
-    // if we have only a single elem in path, given object must be cont. item
-    if (objSearchedIn->ident() != EVR_SQ)
-      return makeOFCondition(OFM_dcmdata, 25, OF_error, "Cannot search item in object being not a sequence");
-    containingSeq = OFstatic_cast(DcmSequenceOfItems*, objSearchedIn);
-  }
-  else
-  {
-    // get containing item from path which is the penultimate in the path
-    OFListIterator(DcmPathNode*) temp = path->end();
-    temp--; temp--;
-    if (*temp == NULL) return EC_IllegalCall; // never happens here...
-    if ( (*temp)->m_obj == NULL ) return EC_IllegalCall;
-    if ( (*temp)->m_obj->ident() != EVR_SQ)
-      return makeOFCondition(OFM_dcmdata, 25, OF_error, "Cannot search item in object being not a sequence");
-    containingSeq = OFstatic_cast(DcmSequenceOfItems*, (*temp)->m_obj);
-  }
-  if (containingSeq == NULL ) return EC_IllegalCall;
-  DcmItem* item2BDeleted = containingSeq->remove(OFstatic_cast(DcmItem*, toDelete->m_obj));
-  if ( item2BDeleted == NULL )
-    return EC_IllegalCall; // should not happen here...
-  delete item2BDeleted; item2BDeleted = NULL;
-  return EC_Normal;
+    DcmSequenceOfItems* containingSeq = NULL;
+    if (path->size() == 1)
+    {
+        // if we have only a single elem in path, given object must be cont. item
+        if (objSearchedIn->ident() != EVR_SQ)
+            return makeOFCondition(OFM_dcmdata, 25, OF_error, "Cannot search item in object being not a sequence");
+        containingSeq = OFstatic_cast(DcmSequenceOfItems*, objSearchedIn);
+    }
+    else
+    {
+        // get containing item from path which is the penultimate in the path
+        OFListIterator(DcmPathNode*) temp = path->end();
+        temp--;
+        temp--;
+        if (*temp == NULL)
+            return EC_IllegalCall; // never happens here...
+        if ((*temp)->m_obj == NULL)
+            return EC_IllegalCall;
+        if ((*temp)->m_obj->ident() != EVR_SQ)
+            return makeOFCondition(OFM_dcmdata, 25, OF_error, "Cannot search item in object being not a sequence");
+        containingSeq = OFstatic_cast(DcmSequenceOfItems*, (*temp)->m_obj);
+    }
+    if (containingSeq == NULL)
+        return EC_IllegalCall;
+    DcmItem* item2BDeleted = containingSeq->remove(OFstatic_cast(DcmItem*, toDelete->m_obj));
+    if (item2BDeleted == NULL)
+        return EC_IllegalCall; // should not happen here...
+    delete item2BDeleted;
+    item2BDeleted = NULL;
+    return EC_Normal;
 }
 
-
 // Helper function that does work for findOrCreatePath()
-OFCondition DcmPathProcessor::findOrCreateItemPath(DcmItem* item,
-                                                   OFString& path)
+OFCondition DcmPathProcessor::findOrCreateItemPath(DcmItem* item, OFString& path)
 {
-  if (item == NULL)
-    return EC_IllegalParameter;
-
-  if (path.empty())
-    return EC_IllegalParameter;
-
-  OFString restPath(path);
-  OFCondition status = EC_Normal;
-  DcmTag tag;
-  OFString privCreator;
-  OFBool newlyCreated = OFFalse; // denotes whether an element was created
-  DcmElement* elem = NULL;
-  DcmPath* currentResult = NULL;
-
-  // parse tag
-  status = DcmPath::parseTagFromPath(restPath, tag);
-  if (status.bad())
-    return status;
+    if (item == NULL)
+        return EC_IllegalParameter;
 
-  // insert element or sequence
-  if ( !(item->tagExists(tag)) ) // do not to overwrite existing tags
-  {
-    if (m_createIfNecessary)
-    {
-      // private tags needs special handling, e.g. checking reservation
-      if (tag.isPrivate() && m_checkPrivateReservations)
-      {
-        status = checkPrivateTagReservation(item, tag);
-        if (status.bad()) return status;
-      }
-      elem = DcmItem::newDicomElement(tag);
-      if (elem == NULL)
-        return EC_IllegalCall;
-      status = item->insert(elem, OFTrue);
-      if (status.bad())
-      {
-        delete elem; elem = NULL;
+    if (path.empty())
+        return EC_IllegalParameter;
+
+    OFString restPath(path);
+    OFCondition status = EC_Normal;
+    DcmTag tag;
+    OFString privCreator;
+    OFBool newlyCreated    = OFFalse; // denotes whether an element was created
+    DcmElement* elem       = NULL;
+    DcmPath* currentResult = NULL;
+
+    // parse tag
+    status = DcmPath::parseTagFromPath(restPath, tag);
+    if (status.bad())
         return status;
-      }
-      newlyCreated = OFTrue;
+
+    // insert element or sequence
+    if (!(item->tagExists(tag))) // do not to overwrite existing tags
+    {
+        if (m_createIfNecessary)
+        {
+            // private tags needs special handling, e.g. checking reservation
+            if (tag.isPrivate())
+            {
+                if (!tag.isPrivateReservation())
+                {
+                    // if this is no reservation, find the private creator and update tag
+                    if (getPrivateCreator(item, tag, privCreator).good() && !privCreator.empty())
+                    {
+                        tag.setPrivateCreator(privCreator.c_str());
+                    }
+                    // now that private creator is hopefully set, lookup vr
+                    tag.lookupVRinDictionary();
+                    // check private reservation if desired
+                    if (m_checkPrivateReservations)
+                    {
+                        status = checkPrivateTagReservation(item, tag.getXTag());
+                        if (status.bad())
+                            return status;
+                    }
+                }
+            }
+            // create element for insertion
+            elem = DcmItem::newDicomElement(tag, privCreator.empty() ? NULL : privCreator.c_str());
+            if (elem == NULL)
+                return EC_IllegalCall;
+            status = item->insert(elem, OFTrue);
+            if (status.bad())
+            {
+                delete elem;
+                elem = NULL;
+                return status;
+            }
+            newlyCreated = OFTrue;
+        }
+        else
+            return EC_TagNotFound;
     }
-    else
-      return EC_TagNotFound;
-  }
-
-  // get element
-  status = item->findAndGetElement(tag, elem);
-  if (status.bad())
-    return EC_CorruptedData; // should not happen
-
-  // start recursion if element was a sequence
-  if (tag.getEVR() == EVR_SQ)
-  {
-    DcmSequenceOfItems* seq = NULL;
-    seq = OFstatic_cast(DcmSequenceOfItems*, elem);
-    if (!seq)
-      status = EC_IllegalCall; // should not happen
-    else
+
+    // get element
+    status = item->findAndGetElement(tag, elem);
+    if (status.bad())
+        return EC_CorruptedData; // should not happen
+
+    // start recursion if element was a sequence
+    if (tag.getEVR() == EVR_SQ)
+    {
+        DcmSequenceOfItems* seq = NULL;
+        seq                     = OFstatic_cast(DcmSequenceOfItems*, elem);
+        if (!seq)
+            status = EC_IllegalCall; // should not happen
+        else
+        {
+            // if sequence could be inserted and there is nothing more to do: add current path to results and return
+            // success
+            if (restPath.empty())
+            {
+                currentResult = new DcmPath(m_currentPath);
+                currentResult->append(new DcmPathNode(elem, 0));
+                m_results.push_back(currentResult);
+                return EC_Normal;
+            }
+            // start recursion if there is path left
+            DcmPathNode* node = new DcmPathNode(seq, 0);
+            m_currentPath.push_back(node);
+            status = findOrCreateSequencePath(seq, restPath);
+            m_currentPath.pop_back(); // avoid side effects
+            delete node;
+        }
+    }
+    else if (restPath.empty()) // we inserted a leaf element: path must be completed
     {
-      // if sequence could be inserted and there is nothing more to do: add current path to results and return success
-      if (restPath.empty())
-      {
+        // add element and add current path to overall results; then return success
         currentResult = new DcmPath(m_currentPath);
-        currentResult->append(new DcmPathNode(elem,0));
+        currentResult->append(new DcmPathNode(elem, 0));
         m_results.push_back(currentResult);
         return EC_Normal;
-      }
-      // start recursion if there is path left
-      DcmPathNode* node = new DcmPathNode(seq, 0);
-      m_currentPath.push_back(node);
-      status = findOrCreateSequencePath(seq, restPath);
-      m_currentPath.pop_back(); // avoid side effects
-      delete node;
-    }
-  }
-  else if (restPath.empty()) // we inserted a leaf element: path must be completed
-  {
-    // add element and add current path to overall results; then return success
-    currentResult = new DcmPath(m_currentPath);
-    currentResult->append(new DcmPathNode(elem, 0));
-    m_results.push_back(currentResult);
-    return EC_Normal;
-  }
-  else // we inserted a leaf element but there is path left -> error
-    status = makeOFCondition(OFM_dcmdata, 25, OF_error, "Invalid Path: Non-sequence tag found with rest path following");
-
-  // in case of errors: delete result path copy and delete DICOM element if it was newly created
-  if ( status.bad() && (elem != NULL) )
-  {
-    m_results.remove(currentResult); // remove from search result
-    if (currentResult)
-    {
-      delete currentResult;
-      currentResult = NULL;
     }
-    if (newlyCreated) // only delete from this dataset and memory if newly created ("undo")
+    else // we inserted a leaf element but there is path left -> error
+        status = makeOFCondition(
+            OFM_dcmdata, 25, OF_error, "Invalid Path: Non-sequence tag found with rest path following");
+
+    // in case of errors: delete result path copy and delete DICOM element if it was newly created
+    if (status.bad() && (elem != NULL))
     {
-      if (item->findAndDeleteElement(tag).bad())
-        delete elem; // delete manually if not found in dataset
+        m_results.remove(currentResult); // remove from search result
+        if (currentResult)
+        {
+            delete currentResult;
+            currentResult = NULL;
+        }
+        if (newlyCreated) // only delete from this dataset and memory if newly created ("undo")
+        {
+            if (item->findAndDeleteElement(tag).bad())
+                delete elem; // delete manually if not found in dataset
+        }
+        elem = NULL;
     }
-    elem = NULL;
-  }
-  return status;
+    return status;
 }
 
-
 // Helper function that does work for findOrCreatePath()
-OFCondition DcmPathProcessor::findOrCreateSequencePath(DcmSequenceOfItems* seq,
-                                                       OFString& path)
+OFCondition DcmPathProcessor::findOrCreateSequencePath(DcmSequenceOfItems* seq, OFString& path)
 {
-  if (seq == NULL)
-    return EC_IllegalParameter;
-
-  // prepare variables
-  OFString restPath(path);
-  OFCondition status = EC_Normal;
-  DcmItem* resultItem = NULL;
-  Uint32 itemNo = 0;
-  Uint32 newlyCreated = 0;    // number of items created (appended) (only non-wildcard mode)
-  Uint32 newPathsCreated = 0; // wildcard mode: number of paths found
-
-  // parse item number
-  OFBool isWildcard = OFFalse;
-  status = DcmPath::parseItemNoFromPath(restPath, itemNo, isWildcard);
-  if (status.bad())
-    return status;
+    if (seq == NULL)
+        return EC_IllegalParameter;
+
+    // prepare variables
+    OFString restPath(path);
+    OFCondition status     = EC_Normal;
+    DcmItem* resultItem    = NULL;
+    Uint32 itemNo          = 0;
+    Uint32 newlyCreated    = 0; // number of items created (appended) (only non-wildcard mode)
+    Uint32 newPathsCreated = 0; // wildcard mode: number of paths found
+
+    // parse item number
+    OFBool isWildcard = OFFalse;
+    status            = DcmPath::parseItemNoFromPath(restPath, itemNo, isWildcard);
+    if (status.bad())
+        return status;
 
-  // wildcard code: add result path for every matching item
-  if (isWildcard)
-  {
-    // if there are no items -> no results are found
-    Uint32 numItems = OFstatic_cast(Uint32, seq->card());
-    if (numItems == 0)
+    // wildcard code: add result path for every matching item
+    if (isWildcard)
     {
-      if (!m_createIfNecessary)
-        return EC_TagNotFound;
-      else
-        return makeOFCondition(OFM_dcmdata, 25, OF_error, "Cannot insert unspecified number (wildcard) of items into sequence");
-    }
-
-    // copy every item to result
-    for (itemNo = 0; itemNo < numItems; itemNo++)
-    {
-      DcmItem* oneItem = seq->getItem(itemNo);
-      /* if we found an item that matches, copy current result path, then
-         add the item found and finally start recursive search for
-         that item.
-       */
-      if (oneItem != NULL)
-      {
-        // if the item was the last thing to parse, add list to results and return
-        if (restPath.empty())
+        // if there are no items -> no results are found
+        Uint32 numItems = OFstatic_cast(Uint32, seq->card());
+        if (numItems == 0)
         {
-          DcmPathNode* itemNode = new DcmPathNode(oneItem, itemNo);
-          DcmPath* currentResult = new DcmPath(m_currentPath);
-          currentResult->append(itemNode);
-          m_results.push_back(currentResult);
-          newPathsCreated++;
+            if (!m_createIfNecessary)
+                return EC_TagNotFound;
+            else
+                return makeOFCondition(
+                    OFM_dcmdata, 25, OF_error, "Cannot insert unspecified number (wildcard) of items into sequence");
         }
-        // else there is path left: continue searching in the new item
-        else
+
+        // copy every item to result
+        for (itemNo = 0; itemNo < numItems; itemNo++)
         {
-         DcmPathNode* itemNode = new DcmPathNode(oneItem, itemNo);
-         m_currentPath.push_back(itemNode);
-         status = findOrCreateItemPath(oneItem, restPath);
-         m_currentPath.pop_back(); // avoid side effects
-         delete itemNode; itemNode = NULL;
-         if (status.bad()) // we did not find the path in that item
-         {
-           if (status != EC_TagNotFound)
-             return status;
-         }
-         else
-         {
-           newPathsCreated++;
-         }
+            DcmItem* oneItem = seq->getItem(itemNo);
+            /* if we found an item that matches, copy current result path, then
+               add the item found and finally start recursive search for
+               that item.
+             */
+            if (oneItem != NULL)
+            {
+                // if the item was the last thing to parse, add list to results and return
+                if (restPath.empty())
+                {
+                    DcmPathNode* itemNode  = new DcmPathNode(oneItem, itemNo);
+                    DcmPath* currentResult = new DcmPath(m_currentPath);
+                    currentResult->append(itemNode);
+                    m_results.push_back(currentResult);
+                    newPathsCreated++;
+                }
+                // else there is path left: continue searching in the new item
+                else
+                {
+                    DcmPathNode* itemNode = new DcmPathNode(oneItem, itemNo);
+                    m_currentPath.push_back(itemNode);
+                    status = findOrCreateItemPath(oneItem, restPath);
+                    m_currentPath.pop_back(); // avoid side effects
+                    delete itemNode;
+                    itemNode = NULL;
+                    if (status.bad()) // we did not find the path in that item
+                    {
+                        if (status != EC_TagNotFound)
+                            return status;
+                    }
+                    else
+                    {
+                        newPathsCreated++;
+                    }
+                }
+            }
+            else // should be possible to get every item, however...
+                return EC_IllegalCall;
         }
-      }
-      else // should be possible to get every item, however...
-        return EC_IllegalCall;
+        // if there was at least one result, success can be returned
+        if (newPathsCreated != 0)
+        {
+            return EC_Normal;
+        }
+        else
+            return EC_TagNotFound;
     }
-    // if there was at least one result, success can be returned
-    if (newPathsCreated != 0)
+
+    /* no wildcard, just select single item or create it if necessary */
+
+    // if item already exists, just grab a reference
+    if (itemNo < seq->card())
+        resultItem = seq->getItem(itemNo);
+    // if item does not exist, create new if desired
+    else if (m_createIfNecessary)
     {
-      return EC_Normal;
+        // create and insert items until desired item count is reached
+        while ((seq->card() <= itemNo) || (status.bad()))
+        {
+            resultItem = new DcmItem();
+            if (!resultItem)
+                return EC_MemoryExhausted;
+            status = seq->insert(resultItem);
+            if (status.bad())
+                delete resultItem;
+            else
+                newlyCreated++;
+        }
     }
+    // item does not exist and should not be created newly, return "path not found"
     else
-      return EC_TagNotFound;
-  }
-
-
-  /* no wildcard, just select single item or create it if necessary */
-
-  // if item already exists, just grab a reference
-  if (itemNo < seq->card())
-    resultItem = seq->getItem(itemNo);
-  // if item does not exist, create new if desired
-  else if (m_createIfNecessary)
-  {
-    // create and insert items until desired item count is reached
-    while ( (seq->card() <= itemNo) || (status.bad()) )
-    {
-      resultItem = new DcmItem();
-      if (!resultItem) return EC_MemoryExhausted;
-      status = seq->insert(resultItem);
-      if (status.bad())
-        delete resultItem;
-      else
-        newlyCreated++;
-    }
-  }
-  // item does not exist and should not be created newly, return "path not found"
-  else
-    return EC_TagNotFound;
-
-  // at this point, the item has been obtained and everything is fine so far
-
-  // finding/creating the path was successful. now check whether there is more to do
-  if (!restPath.empty())
-  {
-    // push new item to result path and continue
-    DcmPathNode* itemNode = new DcmPathNode(resultItem, itemNo);
-    m_currentPath.push_back(itemNode);
-    status = findOrCreateItemPath(resultItem, restPath);
-    m_currentPath.pop_back(); // avoid side effects to input parameter
-    delete itemNode; itemNode = NULL;
-    // in case of no success, delete any items that were newly created and return error
-    if (status.bad())
+        return EC_TagNotFound;
+
+    // at this point, the item has been obtained and everything is fine so far
+
+    // finding/creating the path was successful. now check whether there is more to do
+    if (!restPath.empty())
     {
-      for (Uint32 i=newlyCreated; i > 0; i--)
-      {
-        DcmItem* todelete = seq->remove(i - 1);
-        if (todelete != NULL)
+        // push new item to result path and continue
+        DcmPathNode* itemNode = new DcmPathNode(resultItem, itemNo);
+        m_currentPath.push_back(itemNode);
+        status = findOrCreateItemPath(resultItem, restPath);
+        m_currentPath.pop_back(); // avoid side effects to input parameter
+        delete itemNode;
+        itemNode = NULL;
+        // in case of no success, delete any items that were newly created and return error
+        if (status.bad())
         {
-          delete todelete;
-          todelete = NULL;
+            for (Uint32 i = newlyCreated; i > 0; i--)
+            {
+                DcmItem* todelete = seq->remove(i - 1);
+                if (todelete != NULL)
+                {
+                    delete todelete;
+                    todelete = NULL;
+                }
+            }
+            return status;
         }
-      }
-      return status;
-    }
-  }
-  else // finally everything was successful
-  {
-    DcmPathNode* itemNode = new DcmPathNode(resultItem, itemNo);
-    m_currentPath.push_back(itemNode);
-    m_results.push_back(new DcmPath(m_currentPath));
-    m_currentPath.pop_back(); // avoid side effects
-    delete itemNode; itemNode = NULL;
-    status = EC_Normal;
-  }
-  return status;
+    }
+    else // finally everything was successful
+    {
+        DcmPathNode* itemNode = new DcmPathNode(resultItem, itemNo);
+        m_currentPath.push_back(itemNode);
+        m_results.push_back(new DcmPath(m_currentPath));
+        m_currentPath.pop_back(); // avoid side effects
+        delete itemNode;
+        itemNode = NULL;
+        status   = EC_Normal;
+    }
+    return status;
 }
 
-
-DcmTagKey DcmPathProcessor::calcPrivateReservationTag(const DcmTagKey &privateKey)
+DcmTagKey DcmPathProcessor::calcPrivateReservationTag(const DcmTagKey& privateKey)
 {
-  DcmTagKey reservationTag(0xFFFF, 0xFFFF);
-  // if not a private key is given return "error"
-  if (!privateKey.isPrivate())
+    DcmTagKey reservationTag(0xFFFF, 0xFFFF);
+    // if not a private key is given return "error"
+    if (!privateKey.isPrivate())
+        return reservationTag;
+    // if the private key given is already a reservation key, return it
+    if (privateKey.isPrivateReservation())
+        return privateKey;
+
+    // Calculate corresponding private creator element
+    Uint16 elemNo = privateKey.getElement();
+    // Get yz from given element number wxyz, groups stays the same
+    elemNo = OFstatic_cast(Uint16, elemNo >> 8);
+    reservationTag.setGroup(privateKey.getGroup());
+    reservationTag.setElement(elemNo);
     return reservationTag;
-  // if the private key given is already a reservation key, return it
-  if (privateKey.isPrivateReservation())
-    return privateKey;
-
-  // Calculate corresponding private creator element
-  Uint16 elemNo = privateKey.getElement();
-  // Get yz from given element number wxyz, groups stays the same
-  elemNo = OFstatic_cast(Uint16, elemNo >> 8);
-  reservationTag.setGroup(privateKey.getGroup());
-  reservationTag.setElement(elemNo);
-  return reservationTag;
 }
 
-
-OFCondition DcmPathProcessor::checkPrivateTagReservation(DcmItem* item,
-                                                         const DcmTagKey& tagKey,
-                                                         const OFString& privateCreator)
+OFCondition DcmPathProcessor::getPrivateCreator(DcmItem* item, const DcmTagKey& tagKey, OFString& privateCreator)
 {
-  // if this is already a private reservation, there is nothing to do
-  if (!tagKey.isPrivateReservation())
-  {
-    DcmTagKey reservationKey = calcPrivateReservationTag(tagKey);
-    if (reservationKey == DCM_UndefinedTagKey)
-    {
-      OFString msg("Unable to compute private reservation for tag: "); msg += tagKey.toString();
-      return makeOFCondition(OFM_dcmdata, 25, OF_error, msg.c_str());
-    }
-    if (!item->tagExists(reservationKey))
+    DcmTagKey reservationKey;
+    if (!tagKey.isPrivateReservation())
     {
-      OFString msg("Private reservation missing for tag: "); msg += tagKey.toString();
-      return makeOFCondition(OFM_dcmdata, 25, OF_error, msg.c_str());
+        reservationKey = calcPrivateReservationTag(tagKey);
+        if (reservationKey == DCM_UndefinedTagKey)
+        {
+            OFString msg("Unable to compute private reservation for tag: ");
+            msg += tagKey.toString();
+            return makeOFCondition(OFM_dcmdata, 25, OF_error, msg.c_str());
+        }
+        if (!item->tagExists(reservationKey))
+        {
+            return EC_TagNotFound;
+        }
+        return item->findAndGetOFString(reservationKey, privateCreator);
     }
     else
+        return EC_IllegalCall;
+}
+
+OFCondition
+DcmPathProcessor::checkPrivateTagReservation(DcmItem* item, const DcmTagKey& tagKey, const OFString& privateCreator)
+{
+    OFString actualPrivateCreator;
+    OFCondition result = getPrivateCreator(item, tagKey, actualPrivateCreator);
+    if (result.bad() || actualPrivateCreator.empty())
     {
-      // set private creator for new element
-      OFString actualPrivateCreator;
-      if (item->findAndGetOFString(reservationKey, actualPrivateCreator).bad() || (actualPrivateCreator.empty()))
-      {
-        OFString msg = "Invalid or empty private creator tag: "; msg += reservationKey.toString();
+        OFString msg = "Invalid or empty private creator tag: ";
+        msg += calcPrivateReservationTag(tagKey).toString();
         return makeOFCondition(OFM_dcmdata, 25, OF_error, msg.c_str());
-      }
-      else if (!privateCreator.empty())
-      {
+    }
+    else if (!privateCreator.empty())
+    {
         // check whether private creator is correct
         if (actualPrivateCreator != privateCreator)
         {
-          OFString msg = "Private creator string ("; msg += actualPrivateCreator; msg += ") other than expected ( "; msg += privateCreator; msg += privateCreator;
-          return makeOFCondition(OFM_dcmdata, 25, OF_error, msg.c_str());
+            OFString msg = "Private creator string (";
+            msg += actualPrivateCreator;
+            msg += ") other than expected ( ";
+            msg += privateCreator;
+            msg += privateCreator;
+            return makeOFCondition(OFM_dcmdata, 25, OF_error, msg.c_str());
         }
-      }
     }
-  }
-  return EC_Normal;
-}
-
-
-
-OFCondition DcmPathProcessor::checkPrivateTagReservation(DcmItem* item /* in */,
-                                                         DcmTag& tag /* inout */,
-                                                         const OFString& privateCreator)
-{
-  OFCondition result = checkPrivateTagReservation(item, tag.getXTag(), privateCreator);
-  if (result.good())
-  {
-    // tell tag its private creator and VR
-    tag.setPrivateCreator(privateCreator.c_str());
-    tag.lookupVRinDictionary(); // not done automatically when saving
-  }
-  return result;
+    return EC_Normal;
 }
-
index 7c4024990de2313df982004a69b7d102d977d363..7d1e61550cb2b85db3d72d58955b65063e2481dc 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1997-2019, OFFIS e.V.
+ *  Copyright (C) 1997-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -26,6 +26,7 @@
 #include "dcmtk/dcmdata/dcdeftag.h"
 #include "dcmtk/dcmdata/dcitem.h"
 #include "dcmtk/dcmdata/dcpxitem.h"
+#include "dcmtk/dcmdata/dcjson.h"
 
 //
 // class DcmRepresentationEntry
@@ -89,7 +90,8 @@ DcmPixelData::DcmPixelData(
 {
     repListEnd = repList.end();
     current = original = repListEnd;
-    if (getTag().getEVR() == EVR_ox) setTagVR(EVR_OW);
+    if ((getTag().getEVR() == EVR_ox) || (getTag().getEVR() == EVR_px))
+        setTagVR(EVR_OW);
     unencapsulatedVR = getTag().getEVR();
     recalcVR();
 }
@@ -441,13 +443,20 @@ DcmPixelData::decode(
     DcmStack & pixelStack)
 {
     if (existUnencapsulated) return EC_Normal;
-    OFCondition l_error = DcmCodecList::decode(fromType, fromParam, fromPixSeq, *this, pixelStack);
+    OFBool removeOldPixelRepresentation = OFFalse;
+    OFCondition l_error = DcmCodecList::decode(fromType, fromParam, fromPixSeq, *this, pixelStack, removeOldPixelRepresentation);
     if (l_error.good())
     {
         existUnencapsulated = OFTrue;
         current = repListEnd;
         setVR(EVR_OW);
         recalcVR();
+
+        // the codec has indicated that the image pixel module has been modified
+        // in a way that may affect the validity of the old representation of pixel data.
+        // Thus, we cannot just switch back to the old representation.
+        // Thus, remove old representation(s).
+        if (removeOldPixelRepresentation) removeAllButCurrentRepresentations();
     }
     else
     {
@@ -472,10 +481,11 @@ DcmPixelData::encode(
     if (toType.isEncapsulated())
     {
        DcmPixelSequence * toPixSeq = NULL;
+       OFBool removeOldPixelRepresentation = OFFalse;
        if (fromType.isEncapsulated())
        {
          l_error = DcmCodecList::encode(fromType.getXfer(), fromParam, fromPixSeq,
-                   toType.getXfer(), toParam, toPixSeq, pixelStack);
+                   toType.getXfer(), toParam, toPixSeq, pixelStack, removeOldPixelRepresentation);
        }
        else
        {
@@ -485,7 +495,7 @@ DcmPixelData::encode(
          if (l_error == EC_Normal)
          {
            l_error = DcmCodecList::encode(fromType.getXfer(), pixelData, length,
-                     toType.getXfer(), toParam, toPixSeq, pixelStack);
+                     toType.getXfer(), toParam, toPixSeq, pixelStack, removeOldPixelRepresentation);
          }
        }
 
@@ -494,6 +504,11 @@ DcmPixelData::encode(
            current = insertRepresentationEntry(
              new DcmRepresentationEntry(toType.getXfer(), toParam, toPixSeq));
            recalcVR();
+           // the codec has indicated that the image pixel module has been modified
+           // in a way that may affect the validity of the old representation of pixel data.
+           // Thus, we cannot just switch back to the old representation, but have
+           // to actually decode in this case. Thus, remove old representation(s).
+           if (removeOldPixelRepresentation) removeAllButCurrentRepresentations();
        } else delete toPixSeq;
 
        // if it was possible to convert one encapsulated syntax into
@@ -1270,3 +1285,66 @@ OFBool DcmPixelData::writeUnencapsulated(const E_TransferSyntax xfer)
 
     return existUnencapsulated && isNested();
 }
+
+
+OFCondition DcmPixelData::writeJson(STD_NAMESPACE ostream &out,
+                                             DcmJsonFormat &format)
+{
+
+    // check if we have an empty uncompressed value field.
+    // We never encode that as BulkDataURI.
+    OFBool emptyValue = OFFalse;
+    if ((current == repListEnd) && existUnencapsulated && (getLengthField() == 0))
+    {
+      emptyValue = OFTrue;
+    }
+
+    // now check if the pixel data will be written as
+    // BulkDataURI, which is possible for both uncompressed
+    // and encapsulated pixel data.
+    OFString value;
+    if ((! emptyValue) && format.asBulkDataURI(getTag(), value))
+    {
+        /* write JSON Opener */
+        writeJsonOpener(out, format);
+
+        /* return defined BulkDataURI */
+        format.printBulkDataURIPrefix(out);
+        DcmJsonFormat::printString(out, value);
+
+        /* write JSON Closer */
+        writeJsonCloser(out, format);
+        return EC_Normal;
+    }
+
+    // No bulk data URI, we're supposed to write as InlineBinary.
+    // This is only defined for uncompressed data, not for any of the
+    // encapsulated encodings.
+
+    // check the current pixel data representation
+    if ((current == repListEnd) && existUnencapsulated)
+    {
+      // current pixel data representation is uncompressed (and available).
+
+      /* write JSON Opener */
+      writeJsonOpener(out, format);
+
+      /* for an empty value field, we do not need to do anything */
+      if (getLengthField() > 0)
+      {
+         /* encode binary data as Base64 */
+         format.printInlineBinaryPrefix(out);
+         out << "\"";
+         /* adjust byte order to little endian */
+         Uint8 *byteValues = OFstatic_cast(Uint8 *, getValue(EBO_LittleEndian));
+         OFStandard::encodeBase64(out, byteValues, OFstatic_cast(size_t, getLengthField()));
+         out << "\"";
+      }
+      /* write JSON Closer */
+      writeJsonCloser(out, format);
+      return EC_Normal;
+    }
+
+    // pixel data is encapsulated, return error
+    return EC_CannotWriteJsonInlineBinary;
+}
index d8cdcf1a36179fc246f7d85c9c22ba53edc88f56..42d1f6b67842cea2a9e02c55849b299bca32a207 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2017, OFFIS e.V.
+ *  Copyright (C) 1994-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -240,12 +240,18 @@ OFCondition DcmPixelSequence::insert(DcmPixelItem *item,
     errorFlag = EC_Normal;
     if (item != NULL)
     {
-        itemList->seek_to(where);
-        itemList->insert(item);
-        if (where < itemList->card())
-            DCMDATA_TRACE("DcmPixelSequence::insert() Item at position " << where << " inserted");
-        if (where >= itemList->card())
+        // special case: last position
+        if (where == DCM_EndOfListIndex)
+        {
+            // insert at end of list (avoid seeking)
+            itemList->append(item);
             DCMDATA_TRACE("DcmPixelSequence::insert() Item at last position inserted");
+        } else {
+            // insert after "where"
+            itemList->seek_to(where);
+            itemList->insert(item);
+            DCMDATA_TRACE("DcmPixelSequence::insert() Item at position " << where << " inserted");
+        }
         // check whether the new item already has a parent
         if (item->getParent() != NULL)
         {
index 61fde6beb8251f02041935c4bf4fb9eb7850f291..ffdd14116255fb308902811f9c1cdfa378c31eab 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2002-2019, OFFIS e.V.
+ *  Copyright (C) 2002-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -63,7 +63,8 @@ OFCondition DcmRLECodecDecoder::decode(
     DcmPixelSequence * pixSeq,
     DcmPolymorphOBOW& uncompressedPixelData,
     const DcmCodecParameter * cp,
-    const DcmStack& objStack) const
+    const DcmStack& objStack,
+    OFBool& /* removeOldRep */) const
 {
   OFCondition result = EC_Normal;
 
@@ -704,7 +705,8 @@ OFCondition DcmRLECodecDecoder::encode(
     const DcmRepresentationParameter * /* toRepParam */,
     DcmPixelSequence * & /* pixSeq */,
     const DcmCodecParameter * /* cp */,
-    DcmStack & /* objStack */) const
+    DcmStack & /* objStack */,
+    OFBool& /* removeOldRep */) const
 {
   // we are a decoder only
   return EC_IllegalCall;
@@ -718,7 +720,8 @@ OFCondition DcmRLECodecDecoder::encode(
     const DcmRepresentationParameter * /* toRepParam */,
     DcmPixelSequence * & /* toPixSeq */,
     const DcmCodecParameter * /* cp */,
-    DcmStack & /* objStack */) const
+    DcmStack & /* objStack */,
+    OFBool& /* removeOldRep */) const
 {
   // we don't support re-coding for now.
   return EC_IllegalCall;
index 6d54eff0301c16acb17cf9ede32d67eb8fc85934..30a5a64c8590b2750f4b932c47281be5e6a42610 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2002-2016, OFFIS e.V.
+ *  Copyright (C) 2002-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -71,7 +71,8 @@ OFCondition DcmRLECodecEncoder::decode(
     DcmPixelSequence * /* pixSeq */,
     DcmPolymorphOBOW& /* uncompressedPixelData */,
     const DcmCodecParameter * /* cp */,
-    const DcmStack& /* objStack */) const
+    const DcmStack& /* objStack */,
+    OFBool& /* removeOldRep */ ) const
 {
   // we are an encoder only
   return EC_IllegalCall;
@@ -101,7 +102,8 @@ OFCondition DcmRLECodecEncoder::encode(
     const DcmRepresentationParameter * /* toRepParam */,
     DcmPixelSequence * & /* toPixSeq */,
     const DcmCodecParameter * /* cp */,
-    DcmStack & /* objStack */) const
+    DcmStack& /* objStack */,
+    OFBool& /* removeOldRep */ ) const
 {
   // we don't support re-coding for now.
   return EC_IllegalCall;
@@ -114,7 +116,8 @@ OFCondition DcmRLECodecEncoder::encode(
     const DcmRepresentationParameter * /* toRepParam */ ,
     DcmPixelSequence * & pixSeq,
     const DcmCodecParameter *cp,
-    DcmStack & objStack) const
+    DcmStack& objStack,
+    OFBool& /* removeOldRep */ ) const
 {
   OFCondition result = EC_Normal;
 
index af8f7dbe8379e0f8ddaaff76dc540559cb67b558..840cf6394874cbedf0e70f074f7f6b76e910446a 100644 (file)
@@ -484,11 +484,9 @@ Uint32 DcmSequenceOfItems::getLength(const E_TransferSyntax xfer,
     Uint32 sublen = 0;
     if (!itemList->empty())
     {
-        DcmItem *dI;
         itemList->seek(ELP_first);
         do {
-            dI = OFstatic_cast(DcmItem *, itemList->get());
-            sublen = dI->calcElementLength(xfer, enctype);
+            sublen = itemList->get()->calcElementLength(xfer, enctype);
             /* explicit length: be sure that total size of contained elements fits into sequence's
                32 Bit length field. If not, switch encoding automatically to undefined
                length for this sequence. Nevertheless, any contained items will be
@@ -1046,15 +1044,25 @@ OFCondition DcmSequenceOfItems::insert(DcmItem *item,
     errorFlag = EC_Normal;
     if (item != NULL)
     {
-        itemList->seek_to(where);
-        // insert before or after "where"
-        E_ListPos whichSide = (before) ? (ELP_prev) : (ELP_next);
-        itemList->insert(item, whichSide);
+        // special case: last position
         if (where == DCM_EndOfListIndex)
         {
+            if (before)
+            {
+                // insert before end of list
+                itemList->seek(ELP_last);
+                itemList->prepend(item);
+            } else {
+                // insert at end of list
+                itemList->append(item);
+            }
             DCMDATA_TRACE("DcmSequenceOfItems::insert() Item inserted "
                 << (before ? "before" : "after") << " last position");
         } else {
+            itemList->seek_to(where);
+            // insert before or after "where"
+            E_ListPos whichSide = (before) ? (ELP_prev) : (ELP_next);
+            itemList->insert(item, whichSide);
             DCMDATA_TRACE("DcmSequenceOfItems::insert() Item inserted "
                 << (before ? "before" : "after") << " position " << where);
         }
index 37fa4a7e2e6c69c3025f36adad2452b9d7d41746..278b78f150f8d3047ea517ba93b21b70959ecf73 100644 (file)
@@ -28,8 +28,8 @@ OFCondition swapIfNecessary(const E_ByteOrder newByteOrder,
                             const size_t valWidth)
     /*
      * This function swaps byteLength bytes in value if newByteOrder and oldByteOrder
-     * differ from each other. In case bytes have to be swapped, these bytes are seperated
-     * in valWidth elements which will be swapped seperately.
+     * differ from each other. In case bytes have to be swapped, these bytes are separated
+     * in valWidth elements which will be swapped separately.
      *
      * Parameters:
      *   newByteOrder - [in] The new byte ordering (little or big endian).
@@ -70,8 +70,8 @@ OFCondition swapIfNecessary(const E_ByteOrder newByteOrder,
 void swapBytes(void * value, const Uint32 byteLength,
                const size_t valWidth)
     /*
-     * This function swaps byteLength bytes in value. These bytes are seperated
-     * in valWidth elements which will be swapped seperately.
+     * This function swaps byteLength bytes in value. These bytes are separated
+     * in valWidth elements which will be swapped separately.
      *
      * Parameters:
      *   value        - [in] Array that contains the actual bytes which might have to be swapped.
index 55469ac772d0d690b6c0139a89f2e3b42febe1d9..6e2cb9028408eefc4df88284b47e4a1029e0560b 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -139,6 +139,9 @@ static const UIDNameMap uidNameMap[] = {
     { UID_MPEG4StereoHighProfileLevel4_2TransferSyntax,        "MPEG4StereoHighProfile/Level4.2" },
     { UID_HEVCMainProfileLevel5_1TransferSyntax,               "HEVCMainProfile/Level5.1" },
     { UID_HEVCMain10ProfileLevel5_1TransferSyntax,             "HEVCMain10Profile/Level5.1" },
+    { UID_SMPTEST2110_20_UncompressedProgressiveActiveVideoTransferSyntax, "SMPTEST2110-20:UncompressedProgressiveActiveVideo" },
+    { UID_SMPTEST2110_20_UncompressedInterlacedActiveVideoTransferSyntax, "SMPTEST2110-20:UncompressedInterlacedActiveVideo" },
+    { UID_SMPTEST2110_30_PCMDigitalAudioTransferSyntax,        "SMPTEST2110-30:PCMDigitalAudio" },
     { UID_RFC2557MIMEEncapsulationTransferSyntax,              "RFC2557MIMEEncapsulation" },
     { UID_XMLEncodingTransferSyntax,                           "XMLEncoding" },
     { UID_PrivateGE_LEI_WithBigEndianPixelDataTransferSyntax,  "PrivateGELittleEndianImplicitWithBigEndianPixelData" },
@@ -153,10 +156,12 @@ static const UIDNameMap uidNameMap[] = {
     { UID_BasicTextSRStorage,                                  "BasicTextSRStorage" },
     { UID_BasicVoiceAudioWaveformStorage,                      "BasicVoiceAudioWaveformStorage" },
     { UID_BlendingSoftcopyPresentationStateStorage,            "BlendingSoftcopyPresentationStateStorage" },
+    { UID_BodyPositionWaveformStorage,                         "BodyPositionWaveformStorage" },
     { UID_BreastProjectionXRayImageStorageForPresentation,     "BreastProjectionXRayImageStorageForPresentation" },
     { UID_BreastProjectionXRayImageStorageForProcessing,       "BreastProjectionXRayImageStorageForProcessing" },
     { UID_BreastTomosynthesisImageStorage,                     "BreastTomosynthesisImageStorage" },
     { UID_CardiacElectrophysiologyWaveformStorage,             "CardiacElectrophysiologyWaveformStorage" },
+    { UID_CArmPhotonElectronRadiationRecordStorage,            "CArmPhotonElectronRadiationRecordStorage" },
     { UID_CArmPhotonElectronRadiationStorage,                  "CArmPhotonElectronRadiationStorage" },
     { UID_ChestCADSRStorage,                                   "ChestCADSRStorage" },
     { UID_ColonCADSRStorage,                                   "ColonCADSRStorage" },
@@ -172,13 +177,18 @@ static const UIDNameMap uidNameMap[] = {
     { UID_CTImageStorage,                                      "CTImageStorage" },
     { UID_CTPerformedProcedureProtocolStorage,                 "CTPerformedProcedureProtocolStorage" },
     { UID_DeformableSpatialRegistrationStorage,                "DeformableSpatialRegistrationStorage" },
+    { UID_DermoscopicPhotographyImageStorage,                  "DermoscopicPhotographyImageStorage" },
     { UID_DigitalIntraOralXRayImageStorageForPresentation,     "DigitalIntraOralXRayImageStorageForPresentation" },
     { UID_DigitalIntraOralXRayImageStorageForProcessing,       "DigitalIntraOralXRayImageStorageForProcessing" },
     { UID_DigitalMammographyXRayImageStorageForPresentation,   "DigitalMammographyXRayImageStorageForPresentation" },
     { UID_DigitalMammographyXRayImageStorageForProcessing,     "DigitalMammographyXRayImageStorageForProcessing" },
     { UID_DigitalXRayImageStorageForPresentation,              "DigitalXRayImageStorageForPresentation" },
     { UID_DigitalXRayImageStorageForProcessing,                "DigitalXRayImageStorageForProcessing" },
+    { UID_ElectromyogramWaveformStorage,                       "ElectromyogramWaveformStorage" },
+    { UID_ElectrooculogramWaveformStorage,                     "ElectrooculogramWaveformStorage" },
     { UID_EncapsulatedCDAStorage,                              "EncapsulatedCDAStorage" },
+    { UID_EncapsulatedMTLStorage,                              "EncapsulatedMTLStorage" },
+    { UID_EncapsulatedOBJStorage,                              "EncapsulatedOBJStorage" },
     { UID_EncapsulatedPDFStorage,                              "EncapsulatedPDFStorage" },
     { UID_EncapsulatedSTLStorage,                              "EncapsulatedSTLStorage" },
     { UID_EnhancedCTImageStorage,                              "EnhancedCTImageStorage" },
@@ -214,6 +224,7 @@ static const UIDNameMap uidNameMap[] = {
     { UID_MediaStorageDirectoryStorage,                        "MediaStorageDirectoryStorage" },
     { UID_MRImageStorage,                                      "MRImageStorage" },
     { UID_MRSpectroscopyStorage,                               "MRSpectroscopyStorage" },
+    { UID_MultichannelRespiratoryWaveformStorage,              "MultichannelRespiratoryWaveformStorage" },
     { UID_MultiframeGrayscaleByteSecondaryCaptureImageStorage, "MultiframeGrayscaleByteSecondaryCaptureImageStorage" },
     { UID_MultiframeGrayscaleWordSecondaryCaptureImageStorage, "MultiframeGrayscaleWordSecondaryCaptureImageStorage" },
     { UID_MultiframeSingleBitSecondaryCaptureImageStorage,     "MultiframeSingleBitSecondaryCaptureImageStorage" },
@@ -240,6 +251,9 @@ static const UIDNameMap uidNameMap[] = {
     { UID_RawDataStorage,                                      "RawDataStorage" },
     { UID_RealWorldValueMappingStorage,                        "RealWorldValueMappingStorage" },
     { UID_RespiratoryWaveformStorage,                          "RespiratoryWaveformStorage" },
+    { UID_RoboticArmRadiationStorage,                          "RoboticArmRadiationStorage" },
+    { UID_RoboticRadiationRecordStorage,                       "RoboticRadiationRecordStorage" },
+    { UID_RoutineScalpElectroencephalogramWaveformStorage,     "RoutineScalpElectroencephalogramWaveformStorage" },
     { UID_RTBeamsDeliveryInstructionStorage,                   "RTBeamsDeliveryInstructionStorage" },
     { UID_RTBeamsTreatmentRecordStorage,                       "RTBeamsTreatmentRecordStorage" },
     { UID_RTBrachyApplicationSetupDeliveryInstructionStorage,  "RTBrachyApplicationSetupDeliveryInstructionStorage" },
@@ -250,6 +264,8 @@ static const UIDNameMap uidNameMap[] = {
     { UID_RTIonPlanStorage,                                    "RTIonPlanStorage" },
     { UID_RTPhysicianIntentStorage,                            "RTPhysicianIntentStorage" },
     { UID_RTPlanStorage,                                       "RTPlanStorage" },
+    { UID_RTRadiationRecordSetStorage,                         "RTRadiationRecordSetStorage" },
+    { UID_RTRadiationSalvageRecordStorage,                     "RTRadiationSalvageRecordStorage" },
     { UID_RTRadiationSetStorage,                               "RTRadiationSetStorage" },
     { UID_RTSegmentAnnotationStorage,                          "RTSegmentAnnotationStorage" },
     { UID_RTStructureSetStorage,                               "RTStructureSetStorage" },
@@ -258,6 +274,7 @@ static const UIDNameMap uidNameMap[] = {
     { UID_SegmentationStorage,                                 "SegmentationStorage" },
     { UID_SegmentedVolumeRenderingVolumetricPresentationStateStorage, "SegmentedVolumeRenderingVolumetricPresentationStateStorage" },
     { UID_SimplifiedAdultEchoSRStorage,                        "SimplifiedAdultEchoSRStorage" },
+    { UID_SleepElectroencephalogramWaveformStorage,            "SleepElectroencephalogramWaveformStorage" },
     { UID_SpatialFiducialsStorage,                             "SpatialFiducialsStorage" },
     { UID_SpatialRegistrationStorage,                          "SpatialRegistrationStorage" },
     { UID_SpectaclePrescriptionReportStorage,                  "SpectaclePrescriptionReportStorage" },
@@ -266,6 +283,8 @@ static const UIDNameMap uidNameMap[] = {
     { UID_SurfaceScanMeshStorage,                              "SurfaceScanMeshStorage" },
     { UID_SurfaceScanPointCloudStorage,                        "SurfaceScanPointCloudStorage" },
     { UID_SurfaceSegmentationStorage,                          "SurfaceSegmentationStorage" },
+    { UID_TomotherapeuticRadiationRecordStorage,               "TomotherapeuticRadiationRecordStorage" },
+    { UID_TomotherapeuticRadiationStorage,                     "TomotherapeuticRadiationStorage" },
     { UID_TractographyResultsStorage,                          "TractographyResultsStorage" },
     { UID_TwelveLeadECGWaveformStorage,                        "TwelveLeadECGWaveformStorage" },
     { UID_UltrasoundImageStorage,                              "UltrasoundImageStorage" },
@@ -353,6 +372,7 @@ static const UIDNameMap uidNameMap[] = {
     { UID_UnifiedProcedureStepWatchSOPClass,                   "UnifiedProcedureStepWatchSOPClass" },
     { UID_UnifiedProcedureStepPullSOPClass,                    "UnifiedProcedureStepPullSOPClass" },
     { UID_UnifiedProcedureStepEventSOPClass,                   "UnifiedProcedureStepEventSOPClass" },
+    { UID_UnifiedProcedureStepQuerySOPClass,                   "UnifiedProcedureStepQuerySOPClass" },
     { UID_UPSGlobalSubscriptionSOPInstance,                    "UPSGlobalSubscriptionSOPInstance" },
     { UID_UPSFilteredGlobalSubscriptionSOPInstance,            "UPSFilteredGlobalSubscriptionSOPInstance" },
 
@@ -459,6 +479,12 @@ static const UIDNameMap uidNameMap[] = {
     { UID_DisplaySystemSOPClass,                               "DisplaySystemSOPClass" },
     { UID_DisplaySystemSOPInstance,                            "DisplaySystemSOPInstance" },
 
+    // Real-Time Video
+    { UID_VideoEndoscopicImageRealTimeCommunication,           "VideoEndoscopicImageRealTimeCommunication" },
+    { UID_VideoPhotographicImageRealTimeCommunication,         "VideoPhotographicImageRealTimeCommunication" },
+    { UID_AudioWaveformRealTimeCommunication,                  "AudioWaveformRealTimeCommunication" },
+    { UID_RenditionSelectionDocumentRealTimeCommunication,     "RenditionSelectionDocumentRealTimeCommunication" },
+
     // Other
     { UID_RETIRED_BasicStudyContentNotificationSOPClass,       "RETIRED_BasicStudyContentNotificationSOPClass" },
     { UID_RETIRED_StudyComponentManagementSOPClass,            "RETIRED_StudyComponentManagementSOPClass" },
@@ -533,7 +559,13 @@ static const UIDNameMap uidNameMap[] = {
     { UID_SPM2T2FrameOfReference,                              "SPM2T2FrameOfReference" },
     { UID_SPM2TRANSMFrameOfReference,                          "SPM2TRANSMFrameOfReference" },
     { UID_SPM2WHITEFrameOfReference,                           "SPM2WHITEFrameOfReference" },
+    { UID_StandardRoboticCoordinateSystemFrameOfReference,     "StandardRoboticCoordinateSystemFrameOfReference" },
     { UID_TalairachBrainAtlasFrameOfReference,                 "TalairachBrainAtlasFrameOfReference" },
+    { UID_SRI24FrameOfReference,                               "SRI24FrameOfReferenc" },
+    { UID_Colin27FrameOfReference,                             "Colin27FrameOfReference" },
+    { UID_LPBA40AIRFrameOfReference,                           "LPBA40AIRFrameOfReference" },
+    { UID_LPBA40FLIRTFrameOfReference,                         "LPBA40FLIRTFrameOfReference" },
+    { UID_LPBA40SPM5FrameOfReference,                          "LPBA40SPM5FrameOfReference" },
 
     // UTC Synchronization Frame of Reference
     { UID_UniversalCoordinatedTimeSynchronizationFrameOfReference, "UniversalCoordinatedTimeSynchronizationFrameOfReference" },
@@ -589,10 +621,12 @@ const char* dcmAllStorageSOPClassUIDs[] = {
     UID_BasicTextSRStorage,
     UID_BasicVoiceAudioWaveformStorage,
     UID_BlendingSoftcopyPresentationStateStorage,
+    UID_BodyPositionWaveformStorage,
     UID_BreastProjectionXRayImageStorageForPresentation,
     UID_BreastProjectionXRayImageStorageForProcessing,
     UID_BreastTomosynthesisImageStorage,
     UID_CardiacElectrophysiologyWaveformStorage,
+    UID_CArmPhotonElectronRadiationRecordStorage,
     UID_CArmPhotonElectronRadiationStorage,
     UID_ChestCADSRStorage,
     UID_ColonCADSRStorage,
@@ -606,13 +640,18 @@ const char* dcmAllStorageSOPClassUIDs[] = {
     UID_CTImageStorage,
     UID_CTPerformedProcedureProtocolStorage,
     UID_DeformableSpatialRegistrationStorage,
+    UID_DermoscopicPhotographyImageStorage,
     UID_DigitalIntraOralXRayImageStorageForPresentation,
     UID_DigitalIntraOralXRayImageStorageForProcessing,
     UID_DigitalMammographyXRayImageStorageForPresentation,
     UID_DigitalMammographyXRayImageStorageForProcessing,
     UID_DigitalXRayImageStorageForPresentation,
     UID_DigitalXRayImageStorageForProcessing,
+    UID_ElectromyogramWaveformStorage,
+    UID_ElectrooculogramWaveformStorage,
     UID_EncapsulatedCDAStorage,
+    UID_EncapsulatedMTLStorage,
+    UID_EncapsulatedOBJStorage,
     UID_EncapsulatedPDFStorage,
     UID_EncapsulatedSTLStorage,
     UID_EnhancedCTImageStorage,
@@ -643,6 +682,7 @@ const char* dcmAllStorageSOPClassUIDs[] = {
     UID_MammographyCADSRStorage,
     UID_MRImageStorage,
     UID_MRSpectroscopyStorage,
+    UID_MultichannelRespiratoryWaveformStorage,
     UID_MultiframeGrayscaleByteSecondaryCaptureImageStorage,
     UID_MultiframeGrayscaleWordSecondaryCaptureImageStorage,
     UID_MultiframeSingleBitSecondaryCaptureImageStorage,
@@ -668,6 +708,9 @@ const char* dcmAllStorageSOPClassUIDs[] = {
     UID_RawDataStorage,
     UID_RealWorldValueMappingStorage,
     UID_RespiratoryWaveformStorage,
+    UID_RoboticArmRadiationStorage,
+    UID_RoboticRadiationRecordStorage,
+    UID_RoutineScalpElectroencephalogramWaveformStorage,
     UID_RTBeamsDeliveryInstructionStorage,
     UID_RTBeamsTreatmentRecordStorage,
     UID_RTBrachyApplicationSetupDeliveryInstructionStorage,
@@ -678,6 +721,8 @@ const char* dcmAllStorageSOPClassUIDs[] = {
     UID_RTIonPlanStorage,
     UID_RTPhysicianIntentStorage,
     UID_RTPlanStorage,
+    UID_RTRadiationRecordSetStorage,
+    UID_RTRadiationSalvageRecordStorage,
     UID_RTRadiationSetStorage,
     UID_RTSegmentAnnotationStorage,
     UID_RTStructureSetStorage,
@@ -686,6 +731,7 @@ const char* dcmAllStorageSOPClassUIDs[] = {
     UID_SegmentationStorage,
     UID_SegmentedVolumeRenderingVolumetricPresentationStateStorage,
     UID_SimplifiedAdultEchoSRStorage,
+    UID_SleepElectroencephalogramWaveformStorage,
     UID_SpatialFiducialsStorage,
     UID_SpatialRegistrationStorage,
     UID_SpectaclePrescriptionReportStorage,
@@ -694,6 +740,8 @@ const char* dcmAllStorageSOPClassUIDs[] = {
     UID_SurfaceScanMeshStorage,
     UID_SurfaceScanPointCloudStorage,
     UID_SurfaceSegmentationStorage,
+    UID_TomotherapeuticRadiationRecordStorage,
+    UID_TomotherapeuticRadiationStorage,
     UID_TractographyResultsStorage,
     UID_TwelveLeadECGWaveformStorage,
     UID_UltrasoundImageStorage,
@@ -892,16 +940,24 @@ const char* dcmLongSCUStorageSOPClassUIDs[] = {
     // recently approved
 //  UID_AcquisitionContextSRStorage,
 //  UID_AdvancedBlendingPresentationStateStorage,
+//  UID_BodyPositionWaveformStorage,
 //  UID_BreastProjectionXRayImageStorageForPresentation,
 //  UID_BreastProjectionXRayImageStorageForProcessing,
+//  UID_CArmPhotonElectronRadiationRecordStorage,
 //  UID_CArmPhotonElectronRadiationStorage,
 //  UID_CompositingPlanarMPRVolumetricPresentationStateStorage,
 //  UID_ContentAssessmentResultsStorage,
 //  UID_CornealTopographyMapStorage,
 //  UID_CTPerformedProcedureProtocolStorage,
+//  UID_DermoscopicPhotographyImageStorage,
+//  UID_ElectromyogramWaveformStorage,
+//  UID_ElectrooculogramWaveformStorage,
+//  UID_EncapsulatedMTLStorage,
+//  UID_EncapsulatedOBJStorage,
 //  UID_EncapsulatedSTLStorage,
 //  UID_ExtensibleSRStorage,
 //  UID_GrayscalePlanarMPRVolumetricPresentationStateStorage
+//  UID_MultichannelRespiratoryWaveformStorage,
 //  UID_MultipleVolumeRenderingVolumetricPresentationStateStorage,
 //  UID_OphthalmicOpticalCoherenceTomographyBscanVolumeAnalysisStorage,
 //  UID_OphthalmicOpticalCoherenceTomographyEnFaceImageStorage,
@@ -910,12 +966,20 @@ const char* dcmLongSCUStorageSOPClassUIDs[] = {
 //  UID_PerformedImagingAgentAdministrationSRStorage,
 //  UID_PlannedImagingAgentAdministrationSRStorage,
 //  UID_RadiopharmaceuticalRadiationDoseSRStorage,
+//  UID_RoboticArmRadiationStorage,
+//  UID_RoboticRadiationRecordStorage,
+//  UID_RoutineScalpElectroencephalogramWaveformStorage,
 //  UID_RTBrachyApplicationSetupDeliveryInstructionStorage,
 //  UID_RTPhysicianIntentStorage,
+//  UID_RTRadiationRecordSetStorage,
+//  UID_RTRadiationSalvageRecordStorage,
 //  UID_RTRadiationSetStorage,
 //  UID_RTSegmentAnnotationStorage,
 //  UID_SegmentedVolumeRenderingVolumetricPresentationStateStorage,
 //  UID_SimplifiedAdultEchoSRStorage,
+//  UID_SleepElectroencephalogramWaveformStorage,
+//  UID_TomotherapeuticRadiationRecordStorage,
+//  UID_TomotherapeuticRadiationStorage,
 //  UID_TractographyResultsStorage,
 //  UID_VolumeRenderingVolumetricPresentationStateStorage,
 //  UID_WideFieldOphthalmicPhotographyStereographicProjectionImageStorage,
@@ -1073,6 +1137,7 @@ const char* dcmImageSOPClassUIDs[] = {
     UID_ComputedRadiographyImageStorage,
     UID_CTImageStorage,
     UID_CornealTopographyMapStorage,
+    UID_DermoscopicPhotographyImageStorage,
     UID_DigitalIntraOralXRayImageStorageForPresentation,
     UID_DigitalIntraOralXRayImageStorageForProcessing,
     UID_DigitalMammographyXRayImageStorageForPresentation,
@@ -1169,11 +1234,13 @@ static const DcmModalityTable modalities[] = {
     { UID_BasicTextSRStorage,                                      "SRt", 4096 },
     { UID_BasicVoiceAudioWaveformStorage,                          "AUV", 4096 },
     { UID_BlendingSoftcopyPresentationStateStorage,                "PSb", 4096 },
+    { UID_BodyPositionWaveformStorage,                             "WVb", 4096 },
     { UID_BreastProjectionXRayImageStorageForPresentation,         "BX",  4096 * 4096 * 2 },
     { UID_BreastProjectionXRayImageStorageForProcessing,           "BP",  4096 * 4096 * 2 },
     { UID_BreastTomosynthesisImageStorage,                         "BT",  4096 * 4096 * 2 },
     { UID_CardiacElectrophysiologyWaveformStorage,                 "WVc", 4096 },
-    { UID_CArmPhotonElectronRadiationStorage,                      "RRc", 4096 },
+    { UID_CArmPhotonElectronRadiationRecordStorage,                "RRc", 4096 },
+    { UID_CArmPhotonElectronRadiationStorage,                      "Rca", 4096 },
     { UID_ChestCADSRStorage,                                       "SRh", 4096 },
     { UID_ColonCADSRStorage,                                       "SRo", 4096 },
     { UID_ColorPaletteStorage,                                     "CP",  4096 },
@@ -1188,13 +1255,18 @@ static const DcmModalityTable modalities[] = {
     { UID_CTImageStorage,                                          "CT",  512 * 512 * 2 },
     { UID_CTPerformedProcedureProtocolStorage,                     "PPp", 4096 },
     { UID_DeformableSpatialRegistrationStorage,                    "RGd", 4096 },
+    { UID_DermoscopicPhotographyImageStorage,                      "VLd", 768 * 576 * 3 },
     { UID_DigitalIntraOralXRayImageStorageForPresentation,         "DXo", 1024 * 1024 * 2 },
     { UID_DigitalIntraOralXRayImageStorageForProcessing,           "DPo", 1024 * 1024 * 2 },
     { UID_DigitalMammographyXRayImageStorageForPresentation,       "DXm", 4096 * 4096 * 2 },
     { UID_DigitalMammographyXRayImageStorageForProcessing,         "DPm", 4096 * 4096 * 2 },
     { UID_DigitalXRayImageStorageForPresentation,                  "DX",  2048 * 2048 * 2 },
     { UID_DigitalXRayImageStorageForProcessing,                    "DP",  2048 * 2048 * 2 },
+    { UID_ElectromyogramWaveformStorage,                           "EMG", 4096 },
+    { UID_ElectrooculogramWaveformStorage,                         "EOG", 4096 },
     { UID_EncapsulatedCDAStorage,                                  "CDA", 4096 },
+    { UID_EncapsulatedMTLStorage,                                  "MTL", 4096 },
+    { UID_EncapsulatedOBJStorage,                                  "OBJ", 4096 },
     { UID_EncapsulatedPDFStorage,                                  "PDF", 1024 * 1024 },
     { UID_EncapsulatedSTLStorage,                                  "STL", 4096 },
     { UID_EnhancedCTImageStorage,                                  "CTe", 256 * 512 * 512 },
@@ -1229,6 +1301,7 @@ static const DcmModalityTable modalities[] = {
     { UID_MammographyCADSRStorage,                                 "SRm", 4096 },
     { UID_MRImageStorage,                                          "MR",  256 * 256 * 2 },
     { UID_MRSpectroscopyStorage,                                   "MRs", 256 * 512 * 512 },
+    { UID_MultichannelRespiratoryWaveformStorage,                  "WVm", 4096 },
     { UID_MultiframeGrayscaleByteSecondaryCaptureImageStorage,     "SCb", 512 * 512 },
     { UID_MultiframeGrayscaleWordSecondaryCaptureImageStorage,     "SCw", 512 * 512 * 2 },
     { UID_MultiframeSingleBitSecondaryCaptureImageStorage,         "SCs", 1024 * 1024 },  /* roughly an A4 300dpi scan */
@@ -1255,6 +1328,9 @@ static const DcmModalityTable modalities[] = {
     { UID_RawDataStorage,                                          "RAW", 512 * 512 * 256 },
     { UID_RealWorldValueMappingStorage,                            "RWM", 4096 },
     { UID_RespiratoryWaveformStorage,                              "WVr", 4096 },
+    { UID_RoboticArmRadiationStorage,                              "Rra", 4096 },  /* was RRr */
+    { UID_RoboticRadiationRecordStorage,                           "RRr", 4096 },
+    { UID_RoutineScalpElectroencephalogramWaveformStorage,         "EEG", 4096 },
     { UID_RTBeamsDeliveryInstructionStorage,                       "RTd", 4096 },
     { UID_RTBeamsTreatmentRecordStorage,                           "RTb", 4096 },
     { UID_RTBrachyApplicationSetupDeliveryInstructionStorage,      "RTa", 4096 },
@@ -1265,14 +1341,17 @@ static const DcmModalityTable modalities[] = {
     { UID_RTIonPlanStorage,                                        "RPi", 4096 },
     { UID_RTPlanStorage,                                           "RP" , 4096 },
     { UID_RTPhysicianIntentStorage,                                "RIp", 4096 },
-    { UID_RTRadiationSetStorage,                                   "RRs", 4096 },
-    { UID_RTSegmentAnnotationStorage,                              "RSa", 4096 },
+    { UID_RTRadiationRecordSetStorage,                             "RSr", 4096 },
+    { UID_RTRadiationSalvageRecordStorage,                         "RRs", 4096 },
+    { UID_RTRadiationSetStorage,                                   "RSe", 4096 },  /* was RRs */
+    { UID_RTSegmentAnnotationStorage,                              "RAs", 4096 },  /* was RRs */
     { UID_RTStructureSetStorage,                                   "RS",  4096 },
     { UID_RTTreatmentSummaryRecordStorage,                         "RTs", 4096 },
     { UID_SecondaryCaptureImageStorage,                            "SC",  512 * 512 * 2 },
     { UID_SegmentationStorage,                                     "SG",  4096 },
     { UID_SegmentedVolumeRenderingVolumetricPresentationStateStorage, "VPs", 4096 },
     { UID_SimplifiedAdultEchoSRStorage,                            "SRu", 4096 },
+    { UID_SleepElectroencephalogramWaveformStorage,                "WVs", 4096 },
     { UID_SpatialFiducialsStorage,                                 "FID", 4096 },
     { UID_SpatialRegistrationStorage,                              "RGs", 4096 },
     { UID_SpectaclePrescriptionReportStorage,                      "SRs", 4096 },
@@ -1281,6 +1360,8 @@ static const DcmModalityTable modalities[] = {
     { UID_SurfaceScanMeshStorage,                                  "SSm", 4096 },
     { UID_SurfaceScanPointCloudStorage,                            "SSp", 4096 },
     { UID_SurfaceSegmentationStorage,                              "SGs", 4096 },
+    { UID_TomotherapeuticRadiationRecordStorage,                   "RRt", 4096 },
+    { UID_TomotherapeuticRadiationStorage,                         "Rto", 4096 },  /* was RRt */
     { UID_TractographyResultsStorage,                              "TR",  4096 },
     { UID_TwelveLeadECGWaveformStorage,                            "TLE", 4096 },
     { UID_UltrasoundImageStorage,                                  "US",  512 * 512 },
@@ -1591,14 +1672,14 @@ static long gethostid(void)
     /* get volume information of the system drive */
     char systemDrive[MAX_PATH];
     DWORD serialNumber = 0;
-    if (GetSystemDirectory(systemDrive, OFstatic_cast(UINT, sizeof(systemDrive))) >= 0)
+    if (GetSystemDirectoryA(systemDrive, OFstatic_cast(UINT, sizeof(systemDrive))) >= 0)
     {
         /* check for proper pathname */
         if ((strlen(systemDrive) >= 3) && (systemDrive[1] == ':') && (systemDrive[2] == '\\'))
         {
             /* truncate the pathname directly after the drive specification */
             systemDrive[3] = 0;
-            if (!GetVolumeInformation(systemDrive, NULL, 0, &serialNumber, NULL, NULL, NULL, 0))
+            if (!GetVolumeInformationA(systemDrive, NULL, 0, &serialNumber, NULL, NULL, NULL, 0))
                 serialNumber = 0;
         }
     }
index f27c9343002875988db7d3b89d1608b3339dc234..85398553d5c1cbbc906bf8b44f0e3000d3bb4bc2 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -138,7 +138,8 @@ static const DcmVREntry DcmVRDict[] = {
     { EVR_US, "US", &noDelimiters, sizeof(Uint16), DCMVR_PROP_NONE, 2, 2 },
     { EVR_UT, "UT", &noDelimiters, sizeof(char), DCMVR_PROP_ISASTRING | DCMVR_PROP_EXTENDEDLENGTHENCODING | DCMVR_PROP_ISAFFECTEDBYCHARSET, 0, 4294967294U },
     { EVR_UV, "UV", &noDelimiters, sizeof(Uint64), DCMVR_PROP_EXTENDEDLENGTHENCODING, 8, 8 },
-    { EVR_ox, "ox", &noDelimiters, sizeof(Uint8), DCMVR_PROP_NONSTANDARD | DCMVR_PROP_EXTENDEDLENGTHENCODING, 0, 4294967294U },
+    { EVR_ox, "ox", &noDelimiters, sizeof(Uint8), DCMVR_PROP_NONSTANDARD | DCMVR_PROP_EXTENDEDLENGTHENCODING | DCMVR_PROP_UNDEFINEDLENGTH, 0, 4294967294U },
+    { EVR_px, "px", &noDelimiters, sizeof(Uint8), DCMVR_PROP_NONSTANDARD | DCMVR_PROP_EXTENDEDLENGTHENCODING | DCMVR_PROP_UNDEFINEDLENGTH, 0, 4294967294U },
     { EVR_xs, "xs", &noDelimiters, sizeof(Uint16), DCMVR_PROP_NONSTANDARD, 2, 2 },
     { EVR_lt, "lt", &noDelimiters, sizeof(Uint16), DCMVR_PROP_NONSTANDARD | DCMVR_PROP_EXTENDEDLENGTHENCODING, 0, 4294967294U },
     { EVR_na, "na", &noDelimiters, 0, DCMVR_PROP_NONSTANDARD, 0, 0 },
@@ -283,6 +284,7 @@ DcmVR::getValidEVR() const
                 evr = EVR_OW;
                 break;
             case EVR_ox:
+            case EVR_px:
             case EVR_pixelSQ:
                 evr = EVR_OB;
                 break;
@@ -477,16 +479,17 @@ DcmVR::isEquivalent(const DcmVR& avr) const
     switch (vr)
     {
       case EVR_ox:
+      case EVR_px:
           result = (evr == EVR_OB || evr == EVR_OW);
           break;
       case EVR_lt:
           result = (evr == EVR_OW || evr == EVR_US || evr == EVR_SS);
           break;
       case EVR_OB:
-          result = (evr == EVR_ox);
+          result = (evr == EVR_ox || evr == EVR_px);
           break;
       case EVR_OW:
-          result = (evr == EVR_ox || evr == EVR_lt);
+          result = (evr == EVR_ox || evr == EVR_px || evr == EVR_lt);
           break;
       case EVR_up:
           result = (evr == EVR_UL);
index 428f9a59173b9117734711bfe86a9494b542eaf5..8d94594da8e4f80c99219aa8db0a8e85509fc237 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2018, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -260,31 +260,36 @@ OFCondition DcmAttributeTag::writeJson(STD_NAMESPACE ostream &out,
 {
     // always write JSON Opener
     DcmElement::writeJsonOpener(out, format);
-    Uint16 *uintVals;
-    getUint16Array(uintVals);
-    const unsigned long vm = getVM();
-    // check for empty/invalid value
-    if ((uintVals != NULL) && (vm > 0))
+
+    if (!isEmpty())
     {
-        format.printValuePrefix(out);
-        out << STD_NAMESPACE uppercase << STD_NAMESPACE setfill('0');
-        // print tag values "ggggeeee" in hex mode (upper case!)
-        out << "\"";
-        out << STD_NAMESPACE hex << STD_NAMESPACE setw(4) << (*(uintVals++));
-        out << STD_NAMESPACE setw(4) << (*(uintVals++)) << STD_NAMESPACE dec;
-        out << "\"";
-        for (unsigned long valNo = 1; valNo < vm; valNo++)
+        Uint16 *uintVals;
+        getUint16Array(uintVals);
+        const unsigned long vm = getVM();
+        // check for empty/invalid value
+        if ((uintVals != NULL) && (vm > 0))
         {
-            format.printNextArrayElementPrefix(out);
+            format.printValuePrefix(out);
+            out << STD_NAMESPACE uppercase << STD_NAMESPACE setfill('0');
+            // print tag values "ggggeeee" in hex mode (upper case!)
             out << "\"";
             out << STD_NAMESPACE hex << STD_NAMESPACE setw(4) << (*(uintVals++));
             out << STD_NAMESPACE setw(4) << (*(uintVals++)) << STD_NAMESPACE dec;
             out << "\"";
+            for (unsigned long valNo = 1; valNo < vm; valNo++)
+            {
+                format.printNextArrayElementPrefix(out);
+                out << "\"";
+                out << STD_NAMESPACE hex << STD_NAMESPACE setw(4) << (*(uintVals++));
+                out << STD_NAMESPACE setw(4) << (*(uintVals++)) << STD_NAMESPACE dec;
+                out << "\"";
+            }
+            // reset i/o manipulators
+            out << STD_NAMESPACE nouppercase << STD_NAMESPACE setfill(' ');
+            format.printValueSuffix(out);
         }
-        // reset i/o manipulators
-        out << STD_NAMESPACE nouppercase << STD_NAMESPACE setfill(' ');
-        format.printValueSuffix(out);
     }
+
     // write normal JSON closer
     DcmElement::writeJsonCloser(out, format);
     // always report success
index e8895e76a05879ce8c569f558ae54e01260f25bb..0cf8d7da8595846dd86ffd9e953c8f1e84d4a01f 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2016, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -114,6 +114,9 @@ OFCondition DcmDecimalString::getFloat64(Float64 &doubleVal,
 }
 
 
+// ********************************
+
+
 OFCondition DcmDecimalString::getFloat64Vector(OFVector<Float64> &doubleVals)
 {
     /* get stored value */
@@ -162,6 +165,7 @@ OFCondition DcmDecimalString::getFloat64Vector(OFVector<Float64> &doubleVals)
 }
 
 
+
 // ********************************
 
 
@@ -181,6 +185,58 @@ OFCondition DcmDecimalString::getOFString(OFString &stringVal,
 // ********************************
 
 
+OFCondition DcmDecimalString::putFloat64(const Float64 val,
+                                         const unsigned long pos)
+{
+    return putFloat64Prec(val, pos, 6);
+}
+
+
+OFCondition DcmDecimalString::putFloat64Prec(const Float64 val,
+                                             const unsigned long pos,
+                                             const Uint8 prec,
+                                             const OFBool cutTrailZeroes)
+{
+    if (prec > 100)
+        return EC_IllegalParameter;
+
+    // Reserve enough bytes for conversion (considering high precision values that
+    // might be cut off later, i.e. 16 for integer part, 1 for dot, 14 max precision, 1 for NUL, i.e.
+    char buf[16 + 1 + 14 +1];
+    int written = OFStandard::snprintf(buf, 32, "%.*f", prec, val);
+    if (written > 31 /* NUL not counting in */)
+    {
+        return EC_IllegalParameter;
+    }
+
+    OFString str(buf);
+    if (cutTrailZeroes)
+    {
+        size_t dot = str.find_last_of('.');
+        if (dot != OFString_npos)
+        {
+            size_t last_valid = str.find_last_not_of('0');
+            if (last_valid != str.length() -1)
+            {
+                if (str[last_valid] == '.')
+                    str = str.substr(0, last_valid);
+                else
+                    str = str.substr(0, last_valid+1);
+            }
+        }
+    }
+    if (str.length() > 16)
+    {
+        return EC_IllegalParameter;
+    }
+
+    return putOFStringAtPos(str.c_str(), pos);
+}
+
+
+// ********************************
+
+
 OFCondition DcmDecimalString::writeXML(STD_NAMESPACE ostream &out,
                                        const size_t flags)
 {
@@ -226,9 +282,10 @@ OFCondition DcmDecimalString::writeJson(STD_NAMESPACE ostream &out,
 {
     /* always write JSON Opener */
     writeJsonOpener(out, format);
-    /* write element value (if loaded) */
-    if (valueLoaded())
+
+    if (!isEmpty())
     {
+        /* write element value */
         OFString bulkDataValue;
         if (format.asBulkDataURI(getTag(), bulkDataValue))
         {
@@ -237,32 +294,37 @@ OFCondition DcmDecimalString::writeJson(STD_NAMESPACE ostream &out,
         }
         else
         {
-            /* get string data (without normalization) */
-            char *value_ = OFnullptr;
-            Uint32 length = 0;
-            getString(value_, length);
-            if ((value_ != OFnullptr) && (length > 0))
+            const unsigned long vm = getVM();
+            if (vm > 0)
             {
-                /* explicitly convert to OFString because of possible NULL bytes */
-                OFString value(value_, length);
+                OFString value;
+                OFString vmstring = "1";
                 OFCondition status = getOFString(value, 0L);
                 if (status.bad())
                     return status;
                 format.printValuePrefix(out);
-                DcmJsonFormat::printNumberDecimal(out, value);
-                const unsigned long vm = getVM();
+                // if the value is a proper number, write as JSON number,
+                // otherwise write as JSON string.
+                if (checkStringValue(value, vmstring).good())
+                    DcmJsonFormat::printNumberDecimal(out, value);
+                    else DcmJsonFormat::printValueString(out, value);
                 for (unsigned long valNo = 1; valNo < vm; ++valNo)
                 {
                     status = getOFString(value, valNo);
                     if (status.bad())
                         return status;
                     format.printNextArrayElementPrefix(out);
-                    DcmJsonFormat::printNumberDecimal(out, value);
+                    // if the value is a proper number, write as JSON number,
+                    // otherwise write as JSON string.
+                    if (checkStringValue(value, vmstring).good())
+                        DcmJsonFormat::printNumberDecimal(out, value);
+                        else DcmJsonFormat::printValueString(out, value);
                 }
                 format.printValueSuffix(out);
             }
         }
     }
+
     /* write JSON Closer  */
     writeJsonCloser(out, format);
     /* always report success */
index acf6758cad9da84cf75a9ac574cc2600da240c55..72d9dd5f8ef25e4b5a4c90303d8688234b349f61 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 
 
 #include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
+#include "dcmtk/dcmdata/dcvrfd.h"
 #include "dcmtk/ofstd/ofstream.h"
 #include "dcmtk/ofstd/ofstd.h"
-#include "dcmtk/dcmdata/dcvrfd.h"
+#include "dcmtk/ofstd/ofmath.h"
+#include "dcmtk/dcmdata/dcjson.h"
 
 #define INCLUDE_CSTDIO
 #define INCLUDE_CSTRING
@@ -395,3 +397,57 @@ OFBool DcmFloatingPointDouble::matches(const DcmElement& candidate,
   }
   return OFFalse;
 }
+
+// ********************************
+
+OFCondition DcmFloatingPointDouble::writeJson(STD_NAMESPACE ostream &out,
+                                              DcmJsonFormat &format)
+{
+    /* always write JSON Opener */
+    writeJsonOpener(out, format);
+    /* write element value (if non-empty) */
+    if (!isEmpty())
+    {
+        OFCondition status;
+        const unsigned long vm = getVM();
+
+        if (! format.getJsonExtensionEnabled())
+        {
+          // check if any values is 'inf' or 'nan', and return an error in this case
+          // since the JSON extension that would allow us to write these is not enabled
+          Float64 f = 0.0;
+          for (unsigned long valNo = 1; valNo < vm; ++valNo)
+          {
+            status = getFloat64(f, valNo);
+            if (status.bad()) return status;
+            if ((OFMath::isinf)(f) || (OFMath::isnan)(f)) return EC_CannotWriteJsonNumber;
+          }
+        }
+
+        OFString value;
+        if (format.asBulkDataURI(getTag(), value))
+        {
+            format.printBulkDataURIPrefix(out);
+            DcmJsonFormat::printString(out, value);
+        }
+        else
+        {
+            status = getOFString(value, 0L);
+            if (status.bad()) return status;
+            format.printValuePrefix(out);
+            DcmJsonFormat::printNumberDecimal(out, value);
+            for (unsigned long valNo = 1; valNo < vm; ++valNo)
+            {
+                status = getOFString(value, valNo);
+                if (status.bad()) return status;
+                format.printNextArrayElementPrefix(out);
+                DcmJsonFormat::printNumberDecimal(out, value);
+            }
+            format.printValueSuffix(out);
+        }
+    }
+    /* write JSON Closer  */
+    writeJsonCloser(out, format);
+    /* always report success */
+    return EC_Normal;
+}
index c8673e69b1470516e7cba61fb507fb0b9ab9d0c6..5eb83fafca1bb89bf8c066e9de1f746f4825c937 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 
 
 #include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
+#include "dcmtk/dcmdata/dcvrfl.h"
 #include "dcmtk/ofstd/ofstream.h"
 #include "dcmtk/ofstd/ofstd.h"
-#include "dcmtk/dcmdata/dcvrfl.h"
+#include "dcmtk/ofstd/ofmath.h"
+#include "dcmtk/dcmdata/dcjson.h"
 
 #define INCLUDE_CSTDIO
 #define INCLUDE_CSTRING
@@ -397,3 +399,57 @@ OFBool DcmFloatingPointSingle::matches(const DcmElement& candidate,
   }
   return OFFalse;
 }
+
+// ********************************
+
+OFCondition DcmFloatingPointSingle::writeJson(STD_NAMESPACE ostream &out,
+                                              DcmJsonFormat &format)
+{
+    /* always write JSON Opener */
+    writeJsonOpener(out, format);
+    /* write element value (if non-empty) */
+    if (!isEmpty())
+    {
+        OFCondition status;
+        const unsigned long vm = getVM();
+
+        if (! format.getJsonExtensionEnabled())
+        {
+          // check if any values is 'inf' or 'nan', and return an error in this case
+          // since the JSON extension that would allow us to write these is not enabled
+          Float32 f = 0.0;
+          for (unsigned long valNo = 1; valNo < vm; ++valNo)
+          {
+            status = getFloat32(f, valNo);
+            if (status.bad()) return status;
+            if ((OFMath::isinf)(f) || (OFMath::isnan)(f)) return EC_CannotWriteJsonNumber;
+          }
+        }
+
+        OFString value;
+        if (format.asBulkDataURI(getTag(), value))
+        {
+            format.printBulkDataURIPrefix(out);
+            DcmJsonFormat::printString(out, value);
+        }
+        else
+        {
+            status = getOFString(value, 0L);
+            if (status.bad()) return status;
+            format.printValuePrefix(out);
+            DcmJsonFormat::printNumberDecimal(out, value);
+            for (unsigned long valNo = 1; valNo < vm; ++valNo)
+            {
+                status = getOFString(value, valNo);
+                if (status.bad()) return status;
+                format.printNextArrayElementPrefix(out);
+                DcmJsonFormat::printNumberDecimal(out, value);
+            }
+            format.printValueSuffix(out);
+        }
+    }
+    /* write JSON Closer  */
+    writeJsonCloser(out, format);
+    /* always report success */
+    return EC_Normal;
+}
index 876bbe3d7865ffaa65c63fbbfbf805d6e8565a4f..31c09318d17538d5071ea6e48ad228b32b33ae93 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2018, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -154,9 +154,10 @@ OFCondition DcmIntegerString::writeJson(STD_NAMESPACE ostream &out,
 {
     /* always write JSON Opener */
     writeJsonOpener(out, format);
-    /* write element value (if loaded) */
-    if (valueLoaded())
+
+    if (!isEmpty())
     {
+        /* write element value */
         OFString bulkDataValue;
         if (format.asBulkDataURI(getTag(), bulkDataValue))
         {
@@ -165,32 +166,37 @@ OFCondition DcmIntegerString::writeJson(STD_NAMESPACE ostream &out,
         }
         else
         {
-            /* get string data (without normalization) */
-            char *value_ = NULL;
-            Uint32 length = 0;
-            getString(value_, length);
-            if ((value_ != NULL) && (length > 0))
+            const unsigned long vm = getVM();
+            if (vm > 0)
             {
-                /* explicitly convert to OFString because of possible NULL bytes */
-                OFString value(value_, length);
+                OFString value;
+                OFString vmstring = "1";
                 OFCondition status = getOFString(value, 0L);
                 if (status.bad())
                     return status;
                 format.printValuePrefix(out);
-                DcmJsonFormat::printNumberInteger(out, value);
-                const unsigned long vm = getVM();
+                // if the value is a proper number, write as JSON number,
+                // otherwise write as JSON string.
+                if (checkStringValue(value, vmstring).good())
+                    DcmJsonFormat::printNumberInteger(out, value);
+                    else DcmJsonFormat::printValueString(out, value);
                 for (unsigned long valNo = 1; valNo < vm; ++valNo)
                 {
                     status = getOFString(value, valNo);
                     if (status.bad())
                         return status;
                     format.printNextArrayElementPrefix(out);
-                    DcmJsonFormat::printNumberInteger(out, value);
+                    // if the value is a proper number, write as JSON number,
+                    // otherwise write as JSON string.
+                    if (checkStringValue(value, vmstring).good())
+                        DcmJsonFormat::printNumberInteger(out, value);
+                        else DcmJsonFormat::printValueString(out, value);
                 }
                 format.printValueSuffix(out);
             }
         }
     }
+
     /* write JSON Closer  */
     writeJsonCloser(out, format);
     /* always report success */
index 6ad14ae48cca6802be75ed2c95db3c44b26feb8b..e6c3ddb2c181cd157cfc25d38ac9d3f094cb6549 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -869,7 +869,8 @@ OFCondition DcmOtherByteOtherWord::writeJson(STD_NAMESPACE ostream &out,
             /* encode binary data as Base64 */
             format.printInlineBinaryPrefix(out);
             out << "\"";
-            Uint8 *byteValues = OFstatic_cast(Uint8 *, getValue());
+            /* adjust byte order to little endian */
+            Uint8 *byteValues = OFstatic_cast(Uint8 *, getValue(EBO_LittleEndian));
             OFStandard::encodeBase64(out, byteValues, OFstatic_cast(size_t, getLengthField()));
             out << "\"";
         }
index 1d63ccd8b3c5d12955b0fc7e1e7bbf29ebac342d..b657ffdb053a200c3a42f4bfd81cedef23774b1c 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2013-2019, OFFIS e.V.
+ *  Copyright (C) 2013-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -180,7 +180,8 @@ OFCondition DcmOtherDouble::writeJson(STD_NAMESPACE ostream &out,
             /* encode binary data as Base64 */
             format.printInlineBinaryPrefix(out);
             out << "\"";
-            Uint8 *byteValues = OFstatic_cast(Uint8 *, getValue());
+            /* adjust byte order to little endian */
+            Uint8 *byteValues = OFstatic_cast(Uint8 *, getValue(EBO_LittleEndian));
             OFStandard::encodeBase64(out, byteValues, OFstatic_cast(size_t, getLengthField()));
             out << "\"";
         }
index 8c4e2355b66ae7e038347c412821352acb28f1eb..2661b0bc8de329051415a856e96c05614f683f49 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2002-2019, OFFIS e.V.
+ *  Copyright (C) 2002-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -180,7 +180,8 @@ OFCondition DcmOtherFloat::writeJson(STD_NAMESPACE ostream &out,
             /* encode binary data as Base64 */
             format.printInlineBinaryPrefix(out);
             out << "\"";
-            Uint8 *byteValues = OFstatic_cast(Uint8 *, getValue());
+            /* adjust byte order to little endian */
+            Uint8 *byteValues = OFstatic_cast(Uint8 *, getValue(EBO_LittleEndian));
             OFStandard::encodeBase64(out, byteValues, OFstatic_cast(size_t, getLengthField()));
             out << "\"";
         }
index cbb1b6c612d12554feca5c987a7483f68d85f61f..5a0a37985e1f5ab9c5c66b4286a45d2791aeabfc 100644 (file)
@@ -182,7 +182,8 @@ OFCondition DcmOtherLong::writeJson(STD_NAMESPACE ostream &out,
             /* encode binary data as Base64 */
             format.printInlineBinaryPrefix(out);
             out << "\"";
-            Uint8 *byteValues = OFstatic_cast(Uint8 *, getValue());
+            /* adjust byte order to little endian */
+            Uint8 *byteValues = OFstatic_cast(Uint8 *, getValue(EBO_LittleEndian));
             OFStandard::encodeBase64(out, byteValues, OFstatic_cast(size_t, getLengthField()));
             out << "\"";
         }
index c671732d2a7f5363fa15bd1a8c72ce2e556425d5..59d14566c223941357e8c67e10bf9c661db9d041 100644 (file)
@@ -182,7 +182,8 @@ OFCondition DcmOther64bitVeryLong::writeJson(STD_NAMESPACE ostream &out,
             /* encode binary data as Base64 */
             format.printInlineBinaryPrefix(out);
             out << "\"";
-            Uint8 *byteValues = OFstatic_cast(Uint8 *, getValue());
+            /* adjust byte order to little endian */
+            Uint8 *byteValues = OFstatic_cast(Uint8 *, getValue(EBO_LittleEndian));
             OFStandard::encodeBase64(out, byteValues, OFstatic_cast(size_t, getLengthField()));
             out << "\"";
         }
index 3424ccc68478e393dc4c014f163cc19d350ffcf8..4654d4a880f3cf8225ef714f4a4b97bb52f20cdb 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2017, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -24,6 +24,7 @@
 
 #include "dcmtk/dcmdata/dcjson.h"
 #include "dcmtk/dcmdata/dcvrpn.h"
+#include "dcmtk/ofstd/ofstd.h"
 
 
 // ********************************
@@ -117,7 +118,9 @@ OFCondition DcmPersonName::writeXML(STD_NAMESPACE ostream &out,
     /* PN requires special handling in the Native DICOM Model format */
     if (flags & DCMTypes::XF_useNativeModel)
     {
-        /* write normal XML start tag */
+       const OFBool convertNonASCII = (flags & DCMTypes::XF_convertNonASCII) > 0;
+
+       /* write normal XML start tag */
         DcmElement::writeXMLStartTag(out, flags);
         /* if the value is empty, we do not need to insert any PersonName attribute at all */
         if (!isEmpty())
@@ -159,7 +162,14 @@ OFCondition DcmPersonName::writeXML(STD_NAMESPACE ostream &out,
                                 if (!components[c].empty())
                                 {
                                     /* output name component, e.g. <FamilyName>Onken</FamilyName> */
-                                    out << "<" << compNames[c] << ">" << components[c] << "</" << compNames[c] << ">" << OFendl;
+                                    out << "<" << compNames[c] << ">";
+
+                                    /* check whether conversion to XML markup string is required */
+                                    if (OFStandard::checkForMarkupConversion(components[c], convertNonASCII))
+                                        OFStandard::convertToMarkupStream(out, components[c], convertNonASCII);
+                                    else
+                                        out << components[c];
+                                    out << "</" << compNames[c] << ">" << OFendl;
                                 }
                             }
                             out << "</" << componentGroupNames[cg] << ">" << OFendl; // e.g. </SingleByte>
@@ -325,7 +335,8 @@ OFCondition DcmPersonName::writeJson(STD_NAMESPACE ostream &out,
             const char* componentEnd = it - 1;
             while (*componentEnd == ' ')
                 --componentEnd;
-            out.write(begin, componentEnd - begin + 1);
+            OFString s(begin, 0, componentEnd - begin + 1);
+            DcmJsonFormat::escapeControlCharacters(out, s);
         }
 
         // writes the name of the current component group and all components
index 67df5ee2df1816f1f745a3f02818be6114022a69..fac454898efbc4c486c20f24a931e339450e96bb 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1997-2019, OFFIS e.V.
+ *  Copyright (C) 1997-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -32,7 +32,8 @@ DcmPolymorphOBOW::DcmPolymorphOBOW(
     changeVR(OFFalse),
     currentVR(EVR_OW)
 {
-    if (getTag().getEVR() == EVR_ox || getTag().getEVR() == EVR_lt) setTagVR(EVR_OW);
+    if (getTag().getEVR() == EVR_ox || getTag().getEVR() == EVR_px || getTag().getEVR() == EVR_lt)
+        setTagVR(EVR_OW);
 }
 
 DcmPolymorphOBOW::DcmPolymorphOBOW(const DcmPolymorphOBOW & oldObj)
index 6360a570ded845612af8580fca69cea060d35dc3..3695880edca068209fafb3edde85d38eb674d5c9 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2019, OFFIS e.V.
+ *  Copyright (C) 2019-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 
 
 #include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
+#include "dcmtk/dcmdata/dcvrsv.h"
 
 #include "dcmtk/ofstd/ofstream.h"
-#include "dcmtk/dcmdata/dcvrsv.h"
+#include "dcmtk/dcmdata/dcjson.h"
 
 #define INCLUDE_CSTDIO
 #define INCLUDE_CSTRING
@@ -394,3 +395,65 @@ OFCondition DcmSigned64bitVeryLong::verify(const OFBool autocorrect)
         errorFlag = EC_Normal;
     return errorFlag;
 }
+
+// ********************************
+
+// The largest and smallest number permitted in Javascript
+#define JSON_MAX_SAFE_INTEGER 9007199254740991ll
+#define JSON_MIN_SAFE_INTEGER -9007199254740991ll
+
+OFCondition DcmSigned64bitVeryLong::writeJson(STD_NAMESPACE ostream &out,
+                                              DcmJsonFormat &format)
+{
+    /* always write JSON Opener */
+    writeJsonOpener(out, format);
+
+    if (!isEmpty())
+    {
+
+        /* write element value */
+        OFString bulkDataValue;
+        if (format.asBulkDataURI(getTag(), bulkDataValue))
+        {
+            format.printBulkDataURIPrefix(out);
+            DcmJsonFormat::printString(out, bulkDataValue);
+        }
+        else
+        {
+            const unsigned long vm = getVM();
+            OFString value;
+            Sint64 v = 0;
+
+            OFCondition status = getOFString(value, 0L);
+            if (status.bad()) return status;
+            format.printValuePrefix(out);
+
+            // check if we can represent the value as a JSON number.
+            // JSON numbers should be in the interval [JSON_MAX_SAFE_INTEGER..JSON_MAX_SAFE_INTEGER].
+            status = getSint64(v, 0L);
+            if (status.bad() || (v > JSON_MAX_SAFE_INTEGER) || (v < JSON_MIN_SAFE_INTEGER))
+                DcmJsonFormat::printValueString(out, value);
+                else DcmJsonFormat::printNumberInteger(out, value);
+
+            for (unsigned long valNo = 1; valNo < vm; ++valNo)
+            {
+                status = getOFString(value, valNo);
+                if (status.bad()) return status;
+                format.printNextArrayElementPrefix(out);
+
+                // check if we can represent the value as a JSON number.
+                // JSON numbers should be in the interval [JSON_MAX_SAFE_INTEGER..JSON_MAX_SAFE_INTEGER].
+                status = getSint64(v, valNo);
+                if (status.bad() || (v > JSON_MAX_SAFE_INTEGER) || (v < JSON_MIN_SAFE_INTEGER))
+                    DcmJsonFormat::printValueString(out, value);
+                    else DcmJsonFormat::printNumberInteger(out, value);
+            }
+            format.printValueSuffix(out);
+        }
+    }
+
+    /* write JSON Closer  */
+    writeJsonCloser(out, format);
+    /* always report success */
+    return EC_Normal;
+}
index 501a29026a2e183b53513c1199e665a13c32ce96..de69366091e82fb748090a116528b6c6a7fb181a 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2019, OFFIS e.V.
+ *  Copyright (C) 2019-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 
 
 #include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
+#include "dcmtk/dcmdata/dcvruv.h"
 
 #include "dcmtk/ofstd/ofstream.h"
-#include "dcmtk/dcmdata/dcvruv.h"
+#include "dcmtk/dcmdata/dcjson.h"
 
 #define INCLUDE_CSTDIO
 #define INCLUDE_CSTRING
@@ -393,3 +394,65 @@ OFCondition DcmUnsigned64bitVeryLong::verify(const OFBool autocorrect)
         errorFlag = EC_Normal;
     return errorFlag;
 }
+
+
+// ********************************
+
+// The largest number permitted in Javascript
+#define JSON_MAX_SAFE_INTEGER 9007199254740991ull
+
+OFCondition DcmUnsigned64bitVeryLong::writeJson(STD_NAMESPACE ostream &out,
+                                                DcmJsonFormat &format)
+{
+    /* always write JSON Opener */
+    writeJsonOpener(out, format);
+
+    if (!isEmpty())
+    {
+
+        /* write element value */
+        OFString bulkDataValue;
+        if (format.asBulkDataURI(getTag(), bulkDataValue))
+        {
+            format.printBulkDataURIPrefix(out);
+            DcmJsonFormat::printString(out, bulkDataValue);
+        }
+        else
+        {
+            const unsigned long vm = getVM();
+            OFString value;
+            Uint64 v = 0;
+
+            OFCondition status = getOFString(value, 0L);
+            if (status.bad()) return status;
+            format.printValuePrefix(out);
+
+            // check if we can represent the value as a JSON number.
+            // Unsigned JSON numbers should be <= JSON_MAX_SAFE_INTEGER.
+            status = getUint64(v, 0L);
+            if (status.bad() || (v > JSON_MAX_SAFE_INTEGER))
+                DcmJsonFormat::printValueString(out, value);
+                else DcmJsonFormat::printNumberInteger(out, value);
+
+            for (unsigned long valNo = 1; valNo < vm; ++valNo)
+            {
+                status = getOFString(value, valNo);
+                if (status.bad()) return status;
+                format.printNextArrayElementPrefix(out);
+
+                // check if we can represent the value as a JSON number.
+                // Unsigned JSON numbers should be <= JSON_MAX_SAFE_INTEGER.
+                status = getUint64(v, valNo);
+                if (status.bad() || (v > JSON_MAX_SAFE_INTEGER))
+                    DcmJsonFormat::printValueString(out, value);
+                    else DcmJsonFormat::printNumberInteger(out, value);
+            }
+            format.printValueSuffix(out);
+        }
+    }
+
+    /* write JSON Closer  */
+    writeJsonCloser(out, format);
+    /* always report success */
+    return EC_Normal;
+}
index c1a1c6c41e7fd76ae3bf5446720ff0b125132e15..8e2d79d216c36d86bce9f74cdb298cbc7c349d40 100644 (file)
@@ -1,5 +1,5 @@
 # declare executables
-DCMTK_ADD_EXECUTABLE(dcmdata_tests tests tpread ti2dbmp tchval tpath tvrdatim telemlen tparser tdict tvrds tvrfd tvrpn tvrui tvrol tvrov tvrsv tvruv tstrval tspchrs tparent tfilter tvrcomp tmatch tnewdcme tgenuid)
+DCMTK_ADD_EXECUTABLE(dcmdata_tests tests tpread ti2dbmp tchval tpath tvrdatim telemlen tparser tdict tvrds tvrfd tvrpn tvrui tvrol tvrov tvrsv tvruv tstrval tspchrs tparent tfilter tvrcomp tmatch tnewdcme tgenuid tsequen)
 
 # make sure executables are linked to the corresponding libraries
 DCMTK_TARGET_LINK_MODULES(dcmdata_tests i2d dcmdata oflog ofstd)
index 6f141c65e65fe03dd3c05f6d98b7988b761e8c9b..25fd91d93f80baa0e3aebe93727876f41abf42fb 100644 (file)
@@ -897,6 +897,65 @@ tpread.o: tpread.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmdata/dcvrol.h ../include/dcmtk/dcmdata/dcvrov.h \
  ../include/dcmtk/dcmdata/cmdlnarg.h ../include/dcmtk/dcmdata/dcostrmz.h \
  ../include/dcmtk/dcmdata/dcistrmz.h ../include/dcmtk/dcmdata/dcfcache.h
+tsequen.o: tsequen.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h \
+ ../include/dcmtk/dcmdata/dcuid.h ../include/dcmtk/dcmdata/dcdefine.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../include/dcmtk/dcmdata/dcitem.h ../include/dcmtk/dcmdata/dctypes.h \
+ ../include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../include/dcmtk/dcmdata/dcerror.h ../include/dcmtk/dcmdata/dcxfer.h \
+ ../include/dcmtk/dcmdata/dcvr.h ../include/dcmtk/dcmdata/dctag.h \
+ ../include/dcmtk/dcmdata/dctagkey.h ../include/dcmtk/dcmdata/dcstack.h \
+ ../include/dcmtk/dcmdata/dclist.h ../include/dcmtk/dcmdata/dcpcache.h \
+ ../include/dcmtk/dcmdata/dcdatset.h ../include/dcmtk/dcmdata/dcsequen.h \
+ ../include/dcmtk/dcmdata/dcelem.h ../include/dcmtk/dcmdata/dcpxitem.h \
+ ../include/dcmtk/dcmdata/dcvrobow.h ../include/dcmtk/dcmdata/dcofsetl.h \
+ ../include/dcmtk/dcmdata/dcpixseq.h ../include/dcmtk/dcmdata/dcdeftag.h
 tspchrs.o: tspchrs.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/oftest.h \
  ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
@@ -1197,7 +1256,8 @@ tvrds.o: tvrds.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmdata/dcerror.h ../include/dcmtk/dcmdata/dcxfer.h \
  ../include/dcmtk/dcmdata/dcvr.h ../include/dcmtk/dcmdata/dctag.h \
  ../include/dcmtk/dcmdata/dctagkey.h ../include/dcmtk/dcmdata/dcstack.h \
- ../include/dcmtk/dcmdata/dcdeftag.h
+ ../include/dcmtk/dcmdata/dcdeftag.h ../include/dcmtk/dcmdata/dcitem.h \
+ ../include/dcmtk/dcmdata/dclist.h ../include/dcmtk/dcmdata/dcpcache.h
 tvrfd.o: tvrfd.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/oftest.h \
  ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
index eb0039743ed3de05ec167dfb6e29280c612d4e07..a2f44a66a6bf2c7c530e0e86f67c18a807df97b0 100644 (file)
@@ -24,7 +24,7 @@ I2DLIBS = -li2d
 objs = tests.o tpread.o ti2dbmp.o tchval.o tpath.o tvrdatim.o telemlen.o tparser.o \
        tdict.o tvrds.o tvrfd.o tvrui.o tvrol.o tvrov.o tvrsv.o tvruv.o tstrval.o \
        tspchrs.o tvrpn.o tparent.o tfilter.o tvrcomp.o tmatch.o tnewdcme.o \
-       tgenuid.o
+       tgenuid.o tsequen.o
 
 progs = tests
 
index 13e690d0b211ace92797849d7a2071bf6d3f50c5..af8d6442ef01ea67cc846bd149f58bf6a61cdbb1 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2011-2018, OFFIS e.V.
+ *  Copyright (C) 2011-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -31,7 +31,8 @@
 OFTEST(dcmdata_readingDataDictionary)
 {
     // Does loading the global data dictionary work?
-    OFCHECK(dcmDataDict.isDictionaryLoaded());
+    if (!dcmDataDict.isDictionaryLoaded())
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
 }
 
 OFTEST(dcmdata_usingDataDictionary)
index d275eff8e5bbaa07041e6dc187931af876bf3f34..be26d11c9b7d02138f62f8cdf891180103961e98 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2011-2019, OFFIS e.V.
+ *  Copyright (C) 2011-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -121,6 +121,7 @@ TEST_VR(EVR_UC)
 TEST_VR(EVR_UR)
 TEST_VR(EVR_UT)
 TEST_VR(EVR_ox)
+TEST_VR(EVR_px)
 TEST_VR(EVR_lt)
 TEST_VR(EVR_UNKNOWN)
 TEST_VR(EVR_UN)
index f6cb826e8aab98506cb73973ea5894aef37cdc74..9d5db2c041ce135f68547eb06e1e8653b16b3073 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2011-2019 OFFIS e.V.
+ *  Copyright (C) 2011-2020 OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -34,6 +34,7 @@ OFTEST_REGISTER(dcmdata_decimalString_1);
 OFTEST_REGISTER(dcmdata_decimalString_2);
 OFTEST_REGISTER(dcmdata_decimalString_3);
 OFTEST_REGISTER(dcmdata_decimalString_4);
+OFTEST_REGISTER(dcmdata_decimalString_putFloat64);
 OFTEST_REGISTER(dcmdata_floatingPointDouble);
 OFTEST_REGISTER(dcmdata_personName);
 OFTEST_REGISTER(dcmdata_uniqueIdentifier_1);
@@ -84,11 +85,15 @@ OFTEST_REGISTER(dcmdata_elementLength_EVR_UT);
 OFTEST_REGISTER(dcmdata_elementLength_EVR_lt);
 OFTEST_REGISTER(dcmdata_elementLength_EVR_na);
 OFTEST_REGISTER(dcmdata_elementLength_EVR_ox);
+OFTEST_REGISTER(dcmdata_elementLength_EVR_px);
 OFTEST_REGISTER(dcmdata_elementLength_EVR_up);
 OFTEST_REGISTER(dcmdata_elementLength_EVR_xs);
 OFTEST_REGISTER(dcmdata_elementLength_pixelItem);
 OFTEST_REGISTER(dcmdata_elementLength_pixelSequence);
 OFTEST_REGISTER(dcmdata_elementParent);
+OFTEST_REGISTER(dcmdata_sequenceInsert);
+OFTEST_REGISTER(dcmdata_pixelSequenceInsert);
+OFTEST_REGISTER(dcmdata_findAndGetSequenceItem);
 OFTEST_REGISTER(dcmdata_parser_missingDelimitationItems);
 OFTEST_REGISTER(dcmdata_parser_missingSequenceDelimitationItem_1);
 OFTEST_REGISTER(dcmdata_parser_missingSequenceDelimitationItem_2);
index 9370f302b2c1dcf53b4fa7ea5c18a419cd469bbc..b1cbbea4a934676a2bc664b62cdaf7a0b2de7736 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2012, OFFIS e.V.
+ *  Copyright (C) 2012-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #include "dcmtk/dcmdata/dcdeftag.h"
 #include "dcmtk/dcmdata/dcuid.h"
 #include "dcmtk/dcmdata/dcfilter.h"
+#include "dcmtk/dcmdata/dcdict.h"
 
 
 OFTEST( dcmdata_attribute_filter )
 {
+    // make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
     DcmAttributeFilter ct_filter( DCM_SOPClassUID, UID_CTImageStorage );
     DcmItem item;
 
@@ -45,9 +53,9 @@ OFTEST( dcmdata_attribute_filter )
     // test iterator (array) based range
     const char* filter_range[3] =
     {
-       UID_ComputedRadiographyImageStorage,
-       UID_CTImageStorage,
-       UID_MRImageStorage
+        UID_ComputedRadiographyImageStorage,
+        UID_CTImageStorage,
+        UID_MRImageStorage
     };
 
     // create filter from range (iterators)
index cb8f93c3b6803eb269623a100c8d581c39514a37..e77214d64f7757305442b531df5e81ed3d88f9f0 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2011-2018, OFFIS e.V.
+ *  Copyright (C) 2011-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -437,26 +437,61 @@ static void testExplicitVRinDataset(OFBool useDictionaryVR, OFBool useDictionary
 
 OFTEST(dcmdata_parser_wrongExplicitVRinDataset_default)
 {
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
     testExplicitVRinDataset(OFFalse, OFFalse);
 }
 
 OFTEST(dcmdata_parser_wrongExplicitVRinDataset_defaultVR_dictLen)
 {
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
     testExplicitVRinDataset(OFFalse, OFTrue);
 }
 
 OFTEST(dcmdata_parser_wrongExplicitVRinDataset_dictVR_defaultLen)
 {
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
     testExplicitVRinDataset(OFTrue, OFFalse);
 }
 
 OFTEST(dcmdata_parser_wrongExplicitVRinDataset_preferDataDict)
 {
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
     testExplicitVRinDataset(OFTrue, OFTrue);
 }
 
 OFTEST(dcmdata_parser_undefinedLengthUNSequence)
 {
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
     const Uint8 data[] = {
         // Sequence with undefined length and VR UN => gets read as implicit TS
         TAG_AND_LENGTH(DCM_IconImageSequence, 'U', 'N', UNDEFINED_LENGTH),
index 5b18a928ae53d0417ba2dc2c4f1643b988921a19..0ad8f2e62a5b32d72280cdf6acd661a6d3d3320d 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2008-2017, OFFIS e.V.
+ *  Copyright (C) 2008-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -152,7 +152,6 @@ static OFCondition testPathInsertionsWithWildcard(const OFString& path,
 
 OFTEST(dcmdata_pathAccess)
 {
-
   /* make sure data dictionary is loaded */
   if (!dcmDataDict.isDictionaryLoaded())
   {
index 52c4270a14c6d889d4474382cb3f98c9885b2dc4..2f298658089af0dcdbe2344863ddccac90cda44d 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2018, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -312,7 +312,6 @@ static OFCondition randomRead(OFRandom& rnd, DcmDataset *dset, unsigned char *bu
 
 OFTEST(dcmdata_partialElementAccess)
 {
-
     /* make sure data dictionary is loaded */
     if (!dcmDataDict.isDictionaryLoaded())
     {
diff --git a/dcmdata/tests/tsequen.cc b/dcmdata/tests/tsequen.cc
new file mode 100644 (file)
index 0000000..c903999
--- /dev/null
@@ -0,0 +1,100 @@
+/*
+ *
+ *  Copyright (C) 2019, J. Riesmeier, Oldenburg, Germany
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmdata
+ *
+ *  Author:  Joerg Riesmeier
+ *
+ *  Purpose: test program for class DcmSequence and DcmPixelSequence
+ *
+ */
+
+
+#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
+
+#include "dcmtk/ofstd/oftest.h"
+
+#include "dcmtk/dcmdata/dcitem.h"
+#include "dcmtk/dcmdata/dcdatset.h"
+#include "dcmtk/dcmdata/dcsequen.h"
+#include "dcmtk/dcmdata/dcpxitem.h"
+#include "dcmtk/dcmdata/dcpixseq.h"
+#include "dcmtk/dcmdata/dcdeftag.h"
+
+
+#define NUMBER_OF_ITEMS 99999
+
+
+OFTEST(dcmdata_sequenceInsert)
+{
+    DcmSequenceOfItems sequence(DCM_OtherPatientIDsSequence);
+    /* add a large number of items to the sequence */
+    unsigned long counter = 0;
+    for (unsigned long i = 0; i < NUMBER_OF_ITEMS; ++i)
+    {
+        if (sequence.insert(new DcmItem()).good())
+            ++counter;
+    }
+    /* check whether that worked (for-loop shouldn't take too long) */
+    OFCHECK_EQUAL(counter, NUMBER_OF_ITEMS);
+    /* access specific items (performance should be no issue) */
+    OFCHECK(sequence.getItem(0) != NULL);
+    OFCHECK(sequence.getItem(2) != NULL);
+    OFCHECK(sequence.getItem(NUMBER_OF_ITEMS) == NULL);
+    OFCHECK(sequence.getItem(NUMBER_OF_ITEMS - 1) != NULL);
+    OFCHECK(sequence.getItem(NUMBER_OF_ITEMS - 2) != NULL);
+}
+
+
+OFTEST(dcmdata_pixelSequenceInsert)
+{
+    DcmPixelItem *pixelItem = NULL;
+    DcmPixelSequence pixelSequence(DCM_PixelData);
+    /* add a large number of items to the sequence */
+    unsigned long counter = 0;
+    for (unsigned long i = 0; i < NUMBER_OF_ITEMS; ++i)
+    {
+        if (pixelSequence.insert(new DcmPixelItem(DcmTag(DCM_Item, EVR_OB))).good())
+            ++counter;
+    }
+    /* check whether that worked (for-loop shouldn't take too long) */
+    OFCHECK_EQUAL(counter, NUMBER_OF_ITEMS);
+    /* access specific items (performance should be no issue) */
+    OFCHECK(pixelSequence.getItem(pixelItem, 0).good());
+    OFCHECK(pixelSequence.getItem(pixelItem, 2).good());
+    OFCHECK(pixelSequence.getItem(pixelItem, NUMBER_OF_ITEMS).bad());
+    OFCHECK(pixelSequence.getItem(pixelItem, NUMBER_OF_ITEMS - 1).good());
+    OFCHECK(pixelSequence.getItem(pixelItem, NUMBER_OF_ITEMS - 2).good());
+}
+
+
+OFTEST(dcmdata_findAndGetSequenceItem)
+{
+    DcmDataset dataset;
+    DcmItem *item = NULL;
+    /* first, create a dataset with a sequence and a pixel sequence */
+    OFCHECK(dataset.insertSequenceItem(DCM_OtherPatientIDsSequence, new DcmItem()).good());
+    OFCHECK(dataset.insertSequenceItem(DCM_PixelData, new DcmItem()).good());
+    /* try to retrieve the item from the sequence elements */
+    OFCHECK(dataset.findAndGetSequenceItem(DCM_OtherPatientIDsSequence, item).good());
+    OFCHECK(dataset.findAndGetSequenceItem(DCM_PixelData, item).good());
+    /* the following should fail */
+    OFCHECK(dataset.findAndGetSequenceItem(DCM_OtherPatientIDsSequence, item, 1).bad());
+    OFCHECK(dataset.findAndGetSequenceItem(DCM_PixelData, item, 1).bad());
+    /* then, try to create the items by some other means */
+    OFCHECK(dataset.findOrCreateSequenceItem(DCM_OtherPatientIDsSequence, item, 1).good());
+    OFCHECK(dataset.findOrCreateSequenceItem(DCM_PixelData, item, 1).good());
+    /* now, it should work */
+    OFCHECK(dataset.findAndGetSequenceItem(DCM_OtherPatientIDsSequence, item, 1).good());
+    OFCHECK(dataset.findAndGetSequenceItem(DCM_PixelData, item, 1).good());
+}
index a0b3cc7371c213b5d020939861d0aaf09ace29b0..d8100e300071d31626bfb9318d89a29084376be7 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2019, OFFIS e.V.
+ *  Copyright (C) 2015-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -66,6 +66,7 @@
 #include "dcmtk/dcmdata/dcovlay.h"
 #include "dcmtk/dcmdata/dcpixel.h"
 #include "dcmtk/dcmdata/dcpixseq.h"
+#include "dcmtk/dcmdata/dcdict.h"
 
 
 template <typename StringType>
@@ -845,6 +846,13 @@ static void checkDcmItemAndSequences()
 
 OFTEST(dcmdata_VRCompare)
 {
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
     // Check the different String-based VRs (in the sense that the method
     // putAndInsertOFStringArray() can be used by the test method for initializing
     // the test values.
index 16d21cfa513614ef99c27e015c5d3c98e305788b..2f90bf5fef4b6b2a4d23cf2bdf69c0b11691e2f0 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2002-2013, OFFIS e.V.
+ *  Copyright (C) 2002-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -27,6 +27,7 @@
 #include "dcmtk/dcmdata/dcvrtm.h"
 #include "dcmtk/dcmdata/dcvrdt.h"
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmdata/dcdict.h"
 
 #define CHECK_EQUAL(string) do { \
     strstream << OFStringStream_ends; \
 
 OFTEST(dcmdata_dateTime)
 {
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
     double timeZone;
     OFDate dateVal;
     OFTime timeVal;
index 8c3a15ff3a8041f21e21d21c0557b6fb7e52110e..a9132a341bb33ce477b72e5492eecf8a2552ddb7 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2011, OFFIS e.V.
+ *  Copyright (C) 2011-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #include "dcmtk/ofstd/oftest.h"
 #include "dcmtk/dcmdata/dcvrds.h"
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmdata/dcitem.h"
 
 
 OFTEST(dcmdata_decimalString_1)
 {
-    DcmDecimalString decStr(DCM_ContourData);
+    DcmDecimalString decStr(DCM_ContourData, EVR_DS);
     OFVector<Float64> doubleVals;
     OFCHECK(decStr.putString("1\\2.0\\3.5\\-4.99\\+500.005\\6.66E-01").good());
     OFCHECK(decStr.getFloat64Vector(doubleVals).good());
@@ -44,7 +45,7 @@ OFTEST(dcmdata_decimalString_1)
 
 OFTEST(dcmdata_decimalString_2)
 {
-    DcmDecimalString decStr(DCM_ContourData);
+    DcmDecimalString decStr(DCM_ContourData, EVR_DS);
     OFVector<Float64> doubleVals;
     /* insert a NULL byte into the string */
     OFCHECK(decStr.putString("1\\2.0\\3.5\\-4.99\0\\+500.005\\6.66E-01", 34).good());
@@ -60,7 +61,7 @@ OFTEST(dcmdata_decimalString_2)
 
 OFTEST(dcmdata_decimalString_3)
 {
-    DcmDecimalString decStr(DCM_ContourData);
+    DcmDecimalString decStr(DCM_ContourData, EVR_DS);
     OFVector<Float64> doubleVals;
     /* insert a NULL byte into the string */
     OFCHECK(decStr.putOFStringArray(OFString("1\\2.0\\3.5\\-4.99\0\\+500.005\\6.66E-01", 34)).good());
@@ -76,7 +77,7 @@ OFTEST(dcmdata_decimalString_3)
 
 OFTEST(dcmdata_decimalString_4)
 {
-    DcmDecimalString decStr(DCM_ContourData);
+    DcmDecimalString decStr(DCM_ContourData, EVR_DS);
     OFVector<Float64> doubleVals;
     OFCHECK(decStr.putString("1\\2.0\\3.5\\-4.99\\+500.005\\6.66E-01\\").good());
     OFCHECK_EQUAL(decStr.getVM(), 7);
@@ -89,3 +90,79 @@ OFTEST(dcmdata_decimalString_4)
     OFCHECK(decStr.getFloat64Vector(doubleVals).bad());
     OFCHECK_EQUAL(doubleVals.size(), 4);
 }
+
+
+OFTEST(dcmdata_decimalString_putFloat64)
+{
+    // Test insertion in the beginning
+    OFString testStr;
+    DcmDecimalString decStr(DCM_ContourData, EVR_DS);
+    OFCHECK(decStr.putFloat64(0, 0).good());
+    decStr.getOFStringArray(testStr);
+    OFCHECK(testStr == "0");
+
+    // Test insertion at the end (append)
+    OFCHECK(decStr.putFloat64(0.1, 1).good());
+    decStr.getOFStringArray(testStr);
+    OFCHECK(testStr == "0\\0.1");
+
+    // Test insertion at the end (sparse values in the middle)
+    OFCHECK(decStr.putFloat64(0.5, 5).good());
+    decStr.getOFStringArray(testStr);
+    OFCHECK(testStr == "0\\0.1\\\\\\\\0.5");
+
+    // Test insertion in the middle
+    OFCHECK(decStr.putFloat64(0.3, 3).good());
+    decStr.getOFStringArray(testStr);
+    OFCHECK(testStr == "0\\0.1\\\\0.3\\\\0.5");
+
+    // Test insertion of a long float value (maximum precision)
+    OFCHECK(decStr.putFloat64(0.12345678901234,0).good());
+    decStr.getOFStringArray(testStr);
+    OFCHECK(testStr == "0.123457\\0.1\\\\0.3\\\\0.5");
+
+    // Test insertion of long integer value
+    decStr.clear();
+    OFCHECK(decStr.putFloat64(1234567890123456.0,0).good());
+    decStr.getOFStringArray(testStr);
+    OFCHECK(testStr == "1234567890123456");
+
+    // Test insertion of (max) long negative integer value
+    decStr.clear();
+    OFCHECK(decStr.putFloat64(-123456789012345.0,0).good());
+    decStr.getOFStringArray(testStr);
+    OFCHECK(testStr == "-123456789012345");
+
+    // Error: Try to insert integers longer than 16 bytes
+    // Test insertion of long integer value
+    decStr.clear();
+    OFCHECK(decStr.putFloat64(12345678901234567.0,0).bad());
+
+    // Test insertion of (max) long negative integer value
+    decStr.clear();
+    OFCHECK(decStr.putFloat64(-1234567890123456.0,0).bad());
+
+    // Test insertion of a long float value (maximum precision)
+    decStr.clear();
+    OFCHECK(decStr.putFloat64Prec(0.12345678901234, 0, 14).good());
+    decStr.getOFStringArray(testStr);
+    OFCHECK(testStr == "0.12345678901234");
+
+    // Error: Test insertion of a long float value (> maximum precision which would
+    // result in a DS value > 16 chars.
+    decStr.clear();
+    OFCHECK(decStr.putFloat64Prec(0.123456789012345, 0, 15).bad());
+    decStr.getOFStringArray(testStr);
+
+    // Test whether trailing zeroes are kept if desired
+    decStr.clear();
+    OFCHECK(decStr.putFloat64Prec(0.123400, 0, 6, OFFalse).good());
+    decStr.getOFStringArray(testStr);
+    OFCHECK(testStr == "0.123400");
+
+    // Check DcmItem::putFloat64() for Decimal Strings
+    DcmItem item;
+    OFCHECK(item.putAndInsertFloat64(DcmTag(DCM_ContourData, EVR_DS), 0.1).good());
+    OFCHECK(item.findAndGetOFStringArray(DCM_ContourData, testStr).good());
+    OFCHECK(testStr == "0.1");
+}
diff --git a/dcmect/CMakeLists.txt b/dcmect/CMakeLists.txt
new file mode 100644 (file)
index 0000000..a5023d2
--- /dev/null
@@ -0,0 +1,10 @@
+# declare project
+project(dcmect)
+
+# declare include directories which hold for all subdirectories
+include_directories("${dcmect_SOURCE_DIR}/include" "${dcmfg_SOURCE_DIR}/include" "${dcmiod_SOURCE_DIR}/include" "${dcmdata_SOURCE_DIR}/include" "${ofstd_SOURCE_DIR}/include" "${oflog_SOURCE_DIR}/include" ${ZLIB_INCDIR})
+
+# recurse into subdirectories
+foreach(SUBDIR libsrc include tests)
+  add_subdirectory(${SUBDIR})
+endforeach()
diff --git a/dcmect/Makefile.in b/dcmect/Makefile.in
new file mode 100644 (file)
index 0000000..d17d476
--- /dev/null
@@ -0,0 +1,86 @@
+#
+#      Makefile for dcmect
+#
+
+@SET_MAKE@
+
+SHELL = /bin/sh
+VPATH = @srcdir@:@top_srcdir@/include:@top_srcdir@/@configdir@/include
+srcdir = @srcdir@
+top_srcdir = @top_srcdir@
+configdir = @top_srcdir@/@configdir@
+
+include $(configdir)/@common_makefile@
+
+
+all: include-all libsrc-all tests-all
+
+install: install-doc install-support
+
+install-doc: docs-install
+
+install-data: data-install
+
+install-etc: etc-install
+
+install-include: include-install
+
+install-lib: libsrc-install install-include
+
+install-support: install-data install-etc
+
+
+include-all:
+       (cd include && $(MAKE) ARCH="$(ARCH)" all)
+
+libsrc-all: include-all
+       (cd libsrc && $(MAKE) ARCH="$(ARCH)" all)
+
+tests-all: libsrc-all
+       (cd tests && $(MAKE) ARCH="$(ARCH)" all)
+
+
+check: tests-all
+       (cd tests && $(MAKE) check)
+
+check-exhaustive: tests-all
+       (cd tests && $(MAKE) check-exhaustive)
+
+
+include-install:
+       (cd include && $(MAKE) ARCH="$(ARCH)" install)
+
+libsrc-install: libsrc-all
+       (cd libsrc && $(MAKE) ARCH="$(ARCH)" install)
+
+docs-install:
+       (cd docs && $(MAKE) install)
+
+data-install:
+       (cd data && $(MAKE) install)
+
+etc-install:
+       (cd etc && $(MAKE) install)
+
+
+clean:
+       (cd include && $(MAKE) clean)
+       (cd libsrc && $(MAKE) clean)
+       (cd tests && $(MAKE) clean)
+       (cd docs && $(MAKE) clean)
+       (cd data && $(MAKE) clean)
+       (cd etc && $(MAKE) clean)
+       rm -f $(TRASH)
+
+distclean:
+       (cd include && $(MAKE) distclean)
+       (cd libsrc && $(MAKE) distclean)
+       (cd tests && $(MAKE) distclean)
+       (cd docs && $(MAKE) distclean)
+       (cd data && $(MAKE) distclean)
+       (cd etc && $(MAKE) distclean)
+       rm -f $(DISTTRASH)
+
+dependencies:
+       (cd libsrc && touch $(DEP) && $(MAKE) dependencies)
+       (cd tests && touch $(DEP) && $(MAKE) dependencies)
diff --git a/dcmect/configure b/dcmect/configure
new file mode 100755 (executable)
index 0000000..3877a6a
--- /dev/null
@@ -0,0 +1,53 @@
+#! /bin/sh
+
+parentdir=`pwd`
+thisdir=$parentdir
+
+# The following test constructs relative path from the module
+# directory to the configuration directory. If you know this path
+# you can substitute this with
+# configdir=<relative_path>
+# It is very important that the configdir path is relative.
+
+configdir="configdir"
+
+while test "$parentdir" != "/" -a "$configdir" = "configdir"; do
+       if test -d "$parentdir/config" ; then
+               configdir=$parentdir/config
+       else
+               parentdir=`echo $parentdir | sed 's/\/[^\/]*$//'`
+       fi
+done
+
+if test "$configdir" = "configdir" ; then
+       echo "Cannot find configure directory"
+       exit 1
+fi
+
+if test $# != 0;  then
+       case $1 in
+       -a)
+               shift
+               cd "$configdir"
+               echo "running configure in config-directory"
+               ./configure $*
+               cd $thisdir
+               echo "running configure for this module"
+               sh "$configdir/confmod" --srcdir=. $*
+               ;;
+       -c)
+               shift
+               cd "$configdir"
+               echo "running configure in config-directory"
+               ./configure $*
+               ;;
+       *)
+               echo "running configure for this module"
+               sh "$configdir/confmod" --srcdir=. $*
+               ;;
+       esac
+else
+       echo "running configure for this module"
+       sh "$configdir/confmod" --srcdir=. $*
+fi
+
diff --git a/dcmect/data/Makefile.in b/dcmect/data/Makefile.in
new file mode 100644 (file)
index 0000000..8e3825a
--- /dev/null
@@ -0,0 +1,23 @@
+#
+#      Makefile for dcmect/data
+#
+
+@SET_MAKE@
+
+SHELL = /bin/sh
+srcdir = @srcdir@
+top_srcdir = @top_srcdir@
+configdir = @top_srcdir@/@configdir@
+
+include $(configdir)/@common_makefile@
+
+
+all:
+
+install:
+
+clean:
+       rm -f $(TRASH)
+
+distclean:
+       rm -f $(DISTTRASH)
diff --git a/dcmect/docs/Makefile.in b/dcmect/docs/Makefile.in
new file mode 100644 (file)
index 0000000..159073c
--- /dev/null
@@ -0,0 +1,23 @@
+#
+#      Makefile for dcmect/docs
+#
+
+@SET_MAKE@
+
+SHELL = /bin/sh
+srcdir = @srcdir@
+top_srcdir = @top_srcdir@
+configdir = @top_srcdir@/@configdir@
+
+include $(configdir)/@common_makefile@
+
+
+all:
+
+install:
+
+clean:
+       rm -f $(TRASH)
+
+distclean:
+       rm -f $(DISTTRASH)
diff --git a/dcmect/docs/dcmect.dox b/dcmect/docs/dcmect.dox
new file mode 100644 (file)
index 0000000..bc0c984
--- /dev/null
@@ -0,0 +1,180 @@
+/*!
+
+\page mod_dcmect dcmect: a library for working with Enhanced CT objects
+
+\tableofcontents
+
+\section dcmect_introduction Introduction
+
+This module contains classes to deal with DICOM Enhanced CT objects. It is able
+to create, load and save them. Several checks (as possible) make sure
+that only valid Enhanced CT objects are written. This module makes heavy use of
+the \ref mod_dcmiod "dcmiod" module for managing common IOD attribute as well
+as the \ref mod_dcmfg "dcmfg" module to manage the functional groups required
+forEnhanced CT objects.
+
+The main class of this module is:
+\li \b EctEnhancedCT
+
+\section dcmect_howto_use_dcmect How to use dcmect
+
+The \ref mod_dcmect "dcmect" module offers a main class, \b EctEnhancedCT,
+that should be used as a starting point to load or create Enhanced CT objects.
+The \b EctEnhancedCT class manages its data in a similar way as the related
+Enhanced CT IOD is organized in the standard. It holds a list of modules
+(see \ref dcmect_supported_modules) and a set of functional group macros
+(see \ref dcmect_supported_functional_group_macros) that together make up
+the Enhanced CT object.
+
+\subsection dcmect_creation Creation
+
+In order to create a new Enhanced CT object from scratch, a factory method
+EctEnhancedCT::create() must be used (regular constructor is protected)).
+create() asks for some required information that is needed in any case to
+create valid Enhanced CT objects.
+
+Afterwards, the various attributes in the supported modules can be set.
+There is a get() method for each Module that returns a reference, e.g.
+EctEnhancedCT::getIODPatientModule() to retrieve the Patient Module in
+order to set the attribute Patient's Name (IODPatientModule::setPatientName())
+
+An exception are the attributes of the Enhanced CT Image Module which can be
+set directly using set() methods on the \b EctEnhancedCT class,
+e.g. EctEnhancedCT::setISOCenterPosition().
+
+Functional Groups are added in two ways:
+    -# EctEnhancedCT::addForAllFrames() adds a Functional Group as "shared",
+    i.e. as being valid for all frames that will be part of this Enhanced CT
+    object
+    -# EctEnhancedCT::Frames::addFrame() adds a new frame with pixel data
+    and also takes a set of functional groups that should be added as
+    "per-frame".
+
+After constructing the Enhanced CT object it can be written to a \b DcmItem
+or to a DICOM file (EctEnhancedCT::writeDataset() versus EctEnhancedCT::saveFile()).
+
+\subsection dcmect_reading Reading
+
+An existing Enhanced CT object can be read using the static methods
+EctEnhancedCT::loadFile() (load from DICOM file) or EctEnhancedCT::loadDataset()
+(reading from an existing \b DcmItem object in memory).
+
+For compression see section \ref dcmect_compression "on compression".
+
+\subsection dcmect_saving Saving
+
+An existing Enhanced CT object can be written using the methods
+EctEnhancedCT::saveFile() (save to DICOM file) or EctEnhancedCT::writeDataset()
+(writing to an existing \b DcmItem object in memory). By default, EctEnhancedCT
+writes uncompressed files in transfer syntax Little Endian Explicit.
+
+For compression section \ref dcmect_compression "on compression".
+
+\subsection dcmect_modification Modification
+
+An existing \b EctEnhancedCT object can be modified in memory using the methods
+described above. Note that modification must be done careful and might lead to
+inconsistent objects. That's why it is not the recommended to modify existing
+objects with the \ref mod_dcmect "dcmect" module.
+
+\subsection dcmect_code_example Code Example
+
+The dcmect/tests directory contains a file called t_roundtrip.cc which contains
+code that creates, writes and reads a Enhanced CT object so it is a quite
+complete demo case that shows how to use \ref mod_dcmect "dcmect" module.
+
+\subsection dcmect_compression Compression
+
+The EctEnhancedCT works on uncompressed pixel data. Therefore it first tries
+to decompress a file that is encoded using a compressed ("encapsulated")
+transfer syntax.
+
+DCMTK supports various compressed transfer syntaxes, however, the related
+codecs that perform compression or decompression must be registered first
+by the application that wants to use them. EctEnhancedCT does not automatically
+register those codecs but leaves this to the user of the module. Once the
+codecs are registered, EctEnhancedCT will make use of them when trying to
+decompress the compressed dataset.
+
+See for example the \ref mod_dcmjpeg "dcmjpeg module" to see how registering
+(and later deregistering) codecs work.
+
+When sving, EctEnhancedCT::saveFile() writes the file in Little Endian Explicit
+transfer syntax. By setting its parameter \em writeXfer to a compressed transfer
+syntax, \ref mod_dcmect "dcmect" tries to compress the file before writing. As when
+reading a dataset or file, this only works if the user registered the related
+decompression codecs first.
+
+\section dcmect_supported_modules Supported Modules
+
+The following modules of the Enhanced CT IOD are supported:
+
+\li Patient Module
+\li Patient Study Module
+\li General Study Module
+\li General Series Module
+\li Enhanced CT Series Module
+\li Frame of Reference Module
+\li Synchronization Module
+\li General Equipment Module
+\li Enhanced General Equipment Module
+\li Image Pixel Module
+\li Multi-frame Functional Groups Module
+\li Multi-frame Dimension Module
+\li Acquisition Context Module
+\li Enhanced CT Module
+\li SOP Common Module
+\li Common Instance Reference Module
+
+ The following modules are \e not (yet) supported:
+ \li Enhanced Contrast/Bolus Module
+ \li Cardiac Synchronization Module
+ \li Respiratory Synchronization Module
+ \li Supplemental Palette Color Lookup Table Module
+ \li Device Module
+ \li Specimen Module
+ \li Enhanced Multi-energy CT Acquisition Module
+ \li ICC Profile Module
+ \li Frame Extraction Module
+
+ There might be further unsupported optional modules that have been added to
+ the DICOM Standard after the last update of this documentation.
+
+ \section dcmect_supported_functional_group_macros Supported Functional Group Macros
+
+ The following functional group macros are supported:
+
+\li Pixel Measures
+\li Frame Content
+\li Plane Position (Patient)
+\li Plane Orientation (Patient)
+\li Derivation Image
+\li Frame Anatomy
+\li Frame VOI LUT
+\li Real World Value Mapping
+\li Irradiation Event Identification
+\li CT Image Frame Type
+\li CT Acquisition Type
+\li CT Acquisition Details
+\li CT Table Dynamics
+\li CT Position
+\li CT Geometry
+\li CT Reconstruction
+\li CT Exposure
+\li CT X-Ray Details
+\li CT Pixel Value Transformation
+\li CT Additional X-Ray Source
+\li Temporal Position
+
+The following functional group macros are \e not (yet) support:
+\li Referenced Image
+\li Cardiac Synchronization
+\li Contrast/Bolus Usage
+\li Respiratory Synchronization
+\li Multi-energy CT Processing
+\li Multi-energy CT Characteristics
+
+There might be further unsupported optional functional group macros that have
+been added to the DICOM Standard after the last update of this documentation.
+
+*/
diff --git a/dcmect/etc/Makefile.in b/dcmect/etc/Makefile.in
new file mode 100644 (file)
index 0000000..cca88ee
--- /dev/null
@@ -0,0 +1,23 @@
+#
+#      Makefile for dcmect/etc
+#
+
+@SET_MAKE@
+
+SHELL = /bin/sh
+srcdir = @srcdir@
+top_srcdir = @top_srcdir@
+configdir = @top_srcdir@/@configdir@
+
+include $(configdir)/@common_makefile@
+
+
+all:
+
+install:
+
+clean:
+       rm -f $(TRASH)
+
+distclean:
+       rm -f $(DISTTRASH)
diff --git a/dcmect/include/CMakeLists.txt b/dcmect/include/CMakeLists.txt
new file mode 100644 (file)
index 0000000..ca73554
--- /dev/null
@@ -0,0 +1,2 @@
+# declare installation files
+install(DIRECTORY dcmtk/dcmect DESTINATION "${CMAKE_INSTALL_INCLUDEDIR}/dcmtk" COMPONENT include FILES_MATCHING PATTERN "*.h")
diff --git a/dcmect/include/Makefile.in b/dcmect/include/Makefile.in
new file mode 100644 (file)
index 0000000..7bf0915
--- /dev/null
@@ -0,0 +1,27 @@
+#
+#      Makefile for dcmect/include
+#
+
+@SET_MAKE@
+
+SHELL = /bin/sh
+srcdir = @srcdir@
+top_srcdir = @top_srcdir@
+configdir = @top_srcdir@/@configdir@
+
+include $(configdir)/@common_makefile@
+
+
+all:
+
+install:
+       $(configdir)/mkinstalldirs $(DESTDIR)$(includedir)/dcmtk/dcmect
+       for file in dcmtk/dcmect/*.h ; do \
+               $(INSTALL_DATA) $$file $(DESTDIR)$(includedir)/dcmtk/dcmect ;\
+       done
+
+clean:
+       rm -f $(TRASH)
+
+distclean:
+       rm -f $(DISTTRASH)
diff --git a/dcmect/include/dcmtk/dcmect/def.h b/dcmect/include/dcmtk/dcmect/def.h
new file mode 100644 (file)
index 0000000..c5c6a49
--- /dev/null
@@ -0,0 +1,37 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmect
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Contains preprocessor definitions
+ *
+ */
+
+#ifndef DCMECT_DEF_H
+#define DCMECT_DEF_H
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/ofstd/ofdefine.h"
+
+// definitions for DLL/shared library exports
+
+#ifdef dcmect_EXPORTS
+#define DCMTK_DCMECT_EXPORT DCMTK_DECL_EXPORT
+#else
+#define DCMTK_DCMECT_EXPORT DCMTK_DECL_IMPORT
+#endif
+
+#endif // DCMECT_DEF_H
diff --git a/dcmect/include/dcmtk/dcmect/enhanced_ct.h b/dcmect/include/dcmtk/dcmect/enhanced_ct.h
new file mode 100644 (file)
index 0000000..5e586cc
--- /dev/null
@@ -0,0 +1,808 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmect
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class representing an Enhanced CT object
+ *
+ */
+
+#ifndef DCMECT_ENHANCED_CT_H
+#define DCMECT_ENHANCED_CT_H
+
+#include "dcmtk/config/osconfig.h" // include OS configuration first
+
+#include "dcmtk/dcmect/def.h"
+#include "dcmtk/dcmect/types.h" // for Enhanced CT data types
+#include "dcmtk/dcmfg/fginterface.h"
+#include "dcmtk/dcmiod/iodimage.h"
+#include "dcmtk/dcmiod/modacquisitioncontext.h"
+#include "dcmtk/dcmiod/modenhequipment.h"
+#include "dcmtk/dcmiod/modequipment.h"
+#include "dcmtk/dcmiod/modimagepixel.h"
+#include "dcmtk/dcmiod/modmultiframedimension.h"
+#include "dcmtk/dcmiod/modmultiframefg.h"
+#include "dcmtk/dcmiod/modsynchronisation.h"
+
+class IODGeneralEquipmentModule;
+class FGBase;
+class ConcatenationLoader;
+class ConcatenationCreator;
+
+template <typename>
+class IODImagePixelModule;
+
+/** Class representing an object of the "Enhanced CT SOP Class".
+ *  Supported Modules:
+ *    - Patient (via iodimage.h)
+ *    - Patient Study (via iodimage.h)
+ *    - General Study (via iodimage.h)
+ *    - General Series (via iodimage.h)
+ *    - Enhanced CT Series (via this class)
+ *    - Frame of Reference (via iodimage.h)
+ *    - Synchronization (via modsynchronisation.h)
+ *    - General Equipment (via iodimage.h)
+ *    - Enhanced General Equipment (via modenhequipment.h)
+ *    - Image Pixel (via this class)
+ *    - Multi-frame Functional Groups (via modmultiframefg.h)
+ *    - Multi-frame Dimension (via modmultiframedimension.h)
+ *    - Acquisition Context (via modacquisitioncontext.h)
+ *    - Enhanced CT (via mod_enhanced_ct.h)
+ *    - SOP Common (via iodimage.h)
+ *    - Common Instance Reference (via iodimage.h)
+ *
+ * Modules that are not supported:
+ *     - Enhanced Contrast/Bolus
+ *     - Cardiac Synchronization
+ *     - Respiratory Synchronization
+ *     - Supplemental Palette Color Lookup Table
+ *     - Device
+ *     - Specimen
+ *     - Enhanced Multi-energy CT Acquisition
+ *     - ICC Profile
+ *     - Frame Extraction
+ */
+class DCMTK_DCMECT_EXPORT EctEnhancedCT : public DcmIODImage<IODImagePixelModule<Uint16>, IODImagePixelModule<Sint16> >
+{
+
+public:
+    /** Inner class that offers typed interface to bulk data.
+     */
+    template <typename PixelType>
+    class DCMTK_DCMECT_EXPORT Frames
+    {
+    public:
+        /// Binary pixel type
+        typedef PixelType pixel_type;
+
+        /** Method that adds a frame to the Enhanced CT using the underlying
+         *  binary data type.
+         *  @param  data The frame data
+         *  @param  numPixels The number of pixels (rows * columns) of the frame
+         *  @param  perFrameInformation The per-frame functional groups applying for
+         *  @return EC_Normal if adding was successful, error otherwise
+         */
+        OFCondition addFrame(PixelType* data, const size_t numPixels, const OFVector<FGBase*>& perFrameInformation);
+
+        /** Type-specific getFrame() method that returns Sint16 or Uint16 (whatever
+         *  is used in this Enhanced CT)
+         *  @param  frameNumber The frame number to get, starting from 0
+         *  @return Pointer to typed pixel data
+         */
+        PixelType* getFrame(const size_t frameNumber);
+
+    private:
+        /// Make sure the Enhanced CT object (and no one else) can use the constructor below.
+        friend class EctEnhancedCT;
+
+        /** Create Frames object in EctEnhancedCT (see friend declaration above)
+         *  @param  ct The CT object that will contain the frames
+         */
+        Frames(EctEnhancedCT& ct);
+
+        /// Reference to Enhanced CT object in order to access its pixel data
+        EctEnhancedCT& m_CT;
+    };
+
+    /** Frames can contain Uint16, Sint16 or nothing (i.e.\ error condition)
+     *  at all (in that case OFCondition denotes a corresponding error)
+     */
+    typedef OFvariant<OFCondition, Frames<Uint16>, Frames<Sint16> > FramesType;
+
+    // -------------------- destruction -------------------------------
+
+    /** Destructor, frees memory
+     */
+    virtual ~EctEnhancedCT();
+
+    // -------------------- loading and saving ---------------------
+
+    /** Static method to load a Enhanced CT object from a file.
+     *  The memory of the resulting Enhanced CT object has to be freed by the
+     *  caller.
+     *  @param  filename The file to read from
+     *  @param  ct The resulting Enhanced CT object. NULL if dataset
+     *          could not be read successfully.
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    static OFCondition loadFile(const OFString& filename, EctEnhancedCT*& ct);
+
+    /** Static method to load a Enhanced CT object from a dataset object.
+     *  The memory of the resulting Enhanced CT object has to be freed by the
+     *  caller.
+     *  @param  dataset The dataset to read from
+     *  @param  ct The resulting Enhanced CT object. NULL if dataset
+     *          could not be read successfully.
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    static OFCondition loadDataset(DcmDataset& dataset, EctEnhancedCT*& ct);
+
+    /** Static method to load a concatenation of a DICOM Enhanced CT instance
+     *  into a EctEnhancedCT object.
+     *  @param  cl The ConcatenationLoader instance to be used. Must be configured
+     *          so that load() can be called.
+     *  @param  concatenationUID The Concatenation UID identifying the Concatenation
+     *          within the Concatenations know to ConcatenationLoader cl.
+     *  @param  ct The resulting Enhanced CT object, if loading was successful
+     *  @return EC_Normal if loading was successful, error otherwise
+     */
+    static OFCondition loadConcatenation(ConcatenationLoader& cl, const OFString& concatenationUID, EctEnhancedCT*& ct);
+
+    /** Save current object to given filename
+     *  @param  filename The file to write to
+     *  @param  writeXfer The transfer syntax to be used
+     *  @return EC_Normal if writing was successful, error otherwise.
+     */
+    OFCondition saveFile(const OFString& filename, const E_TransferSyntax writeXfer = EXS_LittleEndianExplicit);
+
+    /** Write current object to given item
+     *  @param  dataset The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise.
+     */
+    OFCondition writeDataset(DcmItem& dataset);
+
+    /** Write current object to a Concatenation.
+     *  @param  cc The Concatenation Creator object to be used. Must be configured
+     *          so that writeNextInstance() is ready to be called.
+     *  @return EC_Normal if writing was successful, error otherwise.
+     */
+    OFCondition writeConcatenation(ConcatenationCreator& cc);
+
+    /** If enabled, functional group structure is checked before actual writing
+     *  is performed in the write() method. Checking might be time consuming
+     *  on functional groups with many frames, though disabling might result in
+     *  invalid functional group structures. Disabling should only be done if the
+     *  user knows that the functional groups are valid, wants to to adapt the
+     *  functional groups manually after calling write() or knows what he's doing
+     *  otherwise.<br>
+     *  Per default, checking is enabled.
+     *  @param  doCheck If OFTrue, checking will be performed. If OFFalse,
+     *          no checks are performed.
+     */
+    virtual void setCheckFGOnWrite(const OFBool doCheck);
+
+    /** Returns whether functional group structure is checked before actual
+     *  writing is performed in the write() method.
+     *  @return OFTrue if checking is performed, OFFalse otherwise
+     */
+    virtual OFBool getCheckFGOnWrite();
+
+    // -------------------- creation ---------------------
+
+    /** Factory method to create an Enhanced CT object from the minimal
+     *  set of information required. The actual frame data is
+     *  added separately.
+     *  The memory of the resulting Enhanced CT object has to be freed by the
+     *  caller.
+     *  @param  ct The resulting Enhanced CT object if provided data is
+     *          valid. Otherwise NULL is returned.
+     *  @param  rows Number of rows of Enhanced CT frame data
+     *  @param  columns Number of rows of Enhanced CT frame data
+     *  @param  signedPixelData Denotes if pixel data is signed (OFTrue, Sint16) or
+     *          unsigned (OFFalse, Uint16)
+     *  @param  imageType1 First value for tag Image Type (0008,0008)
+     *  @param  imageType3 Third Value for tag Image Type (0008,0008). See
+     *          EctTypes::DT_ImageType3_... for Defined Terms.
+     *  @param  imageType4 Fourth Value for tag Image Type (0008,0008). See
+     *          EctTypes::DT_ImageType4_... for Defined Terms.
+     *  @param  instanceNumber The value for tag Instance Number (0020,0013).
+     *  @param  contentQualification The value for tag Content Qualification
+     *          (0018,9004).
+     *  @param  pixelPresentation The value for tag Pixel Presentation (0008,9205).
+     *  @param  volumetricProperties The value for tag Volumetric Properties (0008,9206).
+     *  @param  volumeBasedCalculationTechnique The value for tag Volume Based Calculation
+     *          Technique (0008,9207).
+     *  @param  equipmentInfo Equipment that is responsible for creating the EctEnhancedCT
+     *  @param  acquisitionDateTime The date/time when the acquisition of data started.
+     *          Required if value 1 of Image Type is is ORIGINAL or MIXED; may be present
+     *          otherwise. If empty, value will not be set (default)
+     *  @param  acquisitionDuration The time in seconds needed to complete the acquisition of data.
+     *          Required if value 1 of Image Type is is ORIGINAL or MIXED; may be present
+     *          otherwise. If negative, value will not be set (default)
+     *  @return EC_Normal if creation was successful, error otherwise
+     */
+    static OFCondition create(EctEnhancedCT*& ct,
+                              const Uint16 rows,
+                              const Uint16 columns,
+                              const OFBool signedPixelData,
+                              const EctTypes::E_ImageType1 imageType1,
+                              const OFString& imageType3,
+                              const OFString& imageType4,
+                              const OFString& instanceNumber,
+                              const EctTypes::E_ContentQualification contentQualification,
+                              const EctTypes::E_PixelPresentation pixelPresentation,
+                              const EctTypes::E_VolumetricProperties volumetricProperties,
+                              const OFString& volumeBasedCalculationTechnique,
+                              const IODEnhGeneralEquipmentModule::EquipmentInfo& equipmentInfo,
+                              const OFString& acquisitionDateTime = "",
+                              const Float64& acquisitionDuration  = -1.0);
+
+    // -------------------- access ---------------------
+
+    /** Get number of frames, based on the number of items in the shared
+     *  functional functional groups sequence (i.e.\ the attribute Number of
+     *  Frames) is not trusted).
+     *  @return The number of frames handled by this object
+     */
+    size_t getNumberOfFrames() const;
+
+    /** Perform some basic checking. This method is also invoked when
+     *  writing the object to a DICOM dataset or file.
+     *  @param  checkFGStructure If OFTrue (default), structure of functional
+     *          groups is checked, too.
+     *  @return OFTrue, if no errors were found, OFFalse otherwise.
+     */
+    virtual OFBool check(const OFBool checkFGStructure = OFTrue);
+
+    /** Get access to functional groups. This is meant for reading data from
+     *  functional groups that are not actively managed, i.e.\ made accessible by
+     *  EctEnhancedCT. In rare cases, however, it makes sense to access it
+     *  for writing too, e.g.\ in order to add Stacks; use with care!
+     *  @return Reference to the functional groups
+     */
+    virtual FGInterface& getFunctionalGroups();
+
+    /** Get reference t Concatenation information
+     *  @return Reference to ConcatenationInfo object
+     */
+    virtual IODMultiFrameFGModule::ConcatenationInfo& getConcatenationInfo();
+
+    // -------------------- modification ---------------------
+
+    /** Add a functional group for all frames
+     *  @param  group The group to be added as shared functional group. The
+     *  @return EC_Normal if adding was successful, error otherwise
+     */
+    virtual OFCondition addForAllFrames(const FGBase& group);
+
+    /** Return reference to multi-fame dimension module
+     *  @return Reference to multi-frame dimension module
+     */
+    virtual IODMultiframeDimensionModule& getDimensions();
+
+    /** Return Frames
+     *  @return All frames currently assigned to the object
+     */
+    virtual FramesType getFrames();
+
+    /** Import Patient, Study, and Frame of Reference level information from the
+     *  given item. The method does only import Frame of Reference if Frame of
+     *  Reference (FoR) UID is found in the image (and no error is reported if not).
+     *  The reason is that if the source images of the Enhanced CT do have an
+     *  FoR, the Enhanced CT object must have the same one, so we must import it.
+     *  If the images do not have an FoR, we must not try at all importing it.
+     *  If the log stream is set and valid the, the reason for any error might be
+     *  obtained from the error/warning output.
+     *  @param  dataset Reference to DICOM dataset from which the document
+     *          should be read
+     *  @param  takeOverCharset If OFTrue (default), Specific Character Set is
+     *                          taken over from imported dataset. If it's not
+     *                          present or empty (invalid), the attribute will
+     *                          not be present in this class either.
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition importFromSourceImage(DcmItem& dataset, const OFBool takeOverCharset = OFTrue);
+
+    /** Import Patient, Study, and Frame of Reference level information from the
+     *  given item. The method does only import Frame of Reference if Frame of
+     *  Reference UID is found in the image (and no error is reported if not).
+     *  The reason is that if the source images of the Enhanced CT do have an
+     *  FoR, the Enhanced CT object must have the same one, so we must import it.
+     *  If the images do not have an FoR, we must not try at all importing it.
+     *  The current content of this object is not deleted before reading.
+     *  If the log stream is set and valid the, the reason for any error might be
+     *  obtained from the error/warning output.
+     *  @param  filename Reference to DICOM dataset from which the document
+     *          should be read
+     *  @param  takeOverCharset If OFTrue (default), Specific Character Set is
+     *                          taken over from imported dataset. If it's not
+     *                          present or empty (invalid), the attribute will
+     *                          not be present in this class either.
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition importFromSourceImage(const OFString& filename, const OFBool takeOverCharset = OFTrue);
+
+    // ---------------------- Get / Set modules ----------------------
+
+    /** Get Patient Module
+     *  @return a reference to the IOD Patient Module
+     */
+    virtual IODPatientModule& getIODPatientModule();
+
+    /** Get General Study Module
+     *  @return a reference to the IOD General Study Module
+     */
+    virtual IODGeneralStudyModule& getIODGeneralStudyModule();
+
+    /** Get Patient Study Module
+     *  @return a reference to the IOD Patient Study Module
+     */
+    virtual IODPatientStudyModule& getIODPatientStudyModule();
+
+    /** Get General Series Module
+     *  @return a reference to the IOD General Series Module
+     */
+    virtual IODGeneralSeriesModule& getIODGeneralSeriesModule();
+
+    /** Get Frame of Reference Module
+     *  @return a reference to the IOD Frame of Reference Module
+     */
+    virtual IODFoRModule& getIODFrameOfReferenceModule();
+
+    /** Get Synchronization Module
+     *  @return a reference to the IOD Frame of Reference Module
+     */
+    virtual IODSynchronizationModule& getIODSynchronizationModule();
+
+    /** Set whether Synchronization Module will be enabled when writing
+     *  the Enhanced CT object.
+     *  @param  enabled If OFTrue, Synchronization Module will be written,
+     *          otherwise not.
+     */
+    virtual void setIODSynchronisationModuleEnabled(const OFBool enabled);
+
+    /** Returns whether Synchronization Module is enabled for writing
+     *  the Enhanced CT object.
+     *  @return OFTrue, if Synchronization Module will be written,
+     *          OFFalse otherwise.
+     */
+    virtual OFBool getIODSynchronisationModuleEnabled();
+
+    /** Get General Equipment Module
+     *  @return a reference to the General Equipment Module
+     */
+    virtual IODGeneralEquipmentModule& getIODGeneralEquipmentModule();
+
+    /** Get Enhanced General Equipment Module
+     *  @return a reference to the Enhanced General Equipment Module
+     */
+    virtual IODEnhGeneralEquipmentModule& getIODEnhGeneralEquipmentModule();
+
+    /** Get Multi-frame Functional Groups Module
+     *  @return a reference to the Multi-frame Functional Groups Module
+     */
+    virtual IODMultiFrameFGModule& getIODMultiFrameFGModule();
+
+    /** Get Multi-frame Dimension Module
+     *  @return a reference to the Multi-frame Dimension Module
+     */
+    virtual IODMultiframeDimensionModule& getIODMultiframeDimensionModule();
+
+    /** Get Acquisition Context Module
+     *  @return a reference to the Acquisition Context Module
+     */
+    virtual IODAcquisitionContextModule& getIODAcquisitionContextModule();
+
+    /** Get Common Instance Reference Module
+     *  @return a reference to the Common Instance Reference Module
+     */
+    virtual IODCommonInstanceReferenceModule& getIODCommonInstanceReferenceModule();
+
+    /** Get SOP Common Module
+     *  @return a reference to the SOP Common Module
+     */
+    virtual IODSOPCommonModule& getIODSOPCommonModule();
+
+    // ---------------- CT Image level getter() --------------------
+
+    /** Get Image Type
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getImageType(OFString& value, const long pos);
+
+    /** Get Acquisition Number
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm)
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getAcquisitionNumber(Sint32& value, const unsigned long pos);
+
+    /** Get Acquisition Number
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getAcquisitionNumber(OFString& value, const long pos);
+
+    /** Get Acquisition DateTime
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getAcquisitionDateTime(OFString& value, const long pos);
+
+    /** Get Acquisition Duration
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm)
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getAcquisitionDuration(Float64& value, const unsigned long pos);
+
+    /** Get Acquisition Duration
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getAcquisitionDuration(OFString& value, const long pos);
+
+    /** Get Content Qualification
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getContentQualification(OFString& value, const long pos);
+
+    /** Get Image Comments
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getImageComments(OFString& value, const long pos);
+
+    /** Get Burned In Annotation (if filled in correctly by creator, this
+     *  should always be "NO").
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getBurnedInAnnotation(OFString& value, const long pos);
+
+    /** Get Recognizable Visual Features
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getRecognizableVisualFeatures(OFString& value, const long pos);
+
+    /** Get Lossy Image Compression
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getLossyImageCompression(OFString& value, const long pos);
+
+    /** Get Lossy Image Compression Ratio
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm)
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getLossyImageCompressionRatio(Float64& value, const unsigned long pos);
+
+    /** Get Lossy Image Compression Ratio
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getLossyImageCompressionRatio(OFString& value, const long pos);
+
+    /** Get Lossy Image Compression Method
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getLossyImageCompressionMethod(OFString& value, const long pos);
+
+    /** Get Presentation LUT Shape
+     *  @param  value Reference to variable that should hold the result. Should
+     *          always return the value "IDENTITY" if creator filled in the value
+     *          correctly.
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getPresentationLUTShape(OFString& value, const long pos);
+
+    /** Get Multi-Energy CT Acquisition
+     *  @param  value Reference to variable that should hold the result.
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getMultiEnergyCTAcquisition(OFString& value, const long pos);
+
+    /** Get Pixel Presentation
+     *  @param  value Reference to variable that should hold the result.
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getPixelPresentation(OFString& value, const long pos);
+
+    /** Get Volumetric Properties
+     *  @param  value Reference to variable that should hold the result.
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getVolumetricProperties(OFString& value, const long pos);
+
+    /** Get Volume Based Calculation Technique
+     *  @param  value Reference to variable that should hold the result.
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getVolumeBasedCalculationTechnique(OFString& value, const long pos);
+
+    /** Get Isocenter Position
+     *  @param  value Reference to variable that should hold the result.
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getIsocenterPosition(OFString& value, const long pos);
+
+    /** Get Isocenter Position
+     *  @param  values Reference to variable that should hold the result. Should
+     *          hold 3 values if not empty and filled correctly by the creator of
+     *          the Enhanced CT object.
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getIsocenterPosition(OFVector<Float64>& values);
+
+    /** Get number of rows
+     *  @param  rows The number of rows (output)
+     *  @return EC_Normal if getting was successful, error otherwise
+     */
+    virtual OFCondition getRows(Uint16& rows);
+
+    /** Get number of cols
+     *  @param  cols The number of columns (output)
+     *  @return EC_Normal if getting was successful, error otherwise
+     */
+    virtual OFCondition getColumns(Uint16& cols);
+
+    // ---------------- Setters() --------------------
+
+    virtual OFCondition setImageType(const OFString& value, const OFBool check = OFTrue);
+
+    virtual OFCondition setAcquisitionNumber(const OFString& value, const OFBool check = OFTrue);
+
+    virtual OFCondition setAcquisitionDateTime(const OFString& value, const OFBool check = OFTrue);
+
+    virtual OFCondition setAcquisitionDuration(const Float64& value, const OFBool check = OFTrue);
+
+    virtual OFCondition setContentQualification(const EctTypes::E_ContentQualification value,
+                                                const OFBool check = OFTrue);
+
+    virtual OFCondition setImageComments(const OFString& value, const OFBool check = OFTrue);
+
+    virtual OFCondition setRecognizableVisualFeatures(const EctTypes::E_RecognizableVisualFeatures value,
+                                                      const OFBool check = OFTrue);
+
+    /** Set lossy compression flag of the image to "00" or "01" If set to "01",
+     *  ratios and methods have to be provided, too.
+     *  @param  isLossy If OFTrue, Lossy Image Compression is set to "01", otherwise
+     *          to "00".
+     *  @param  ratios Compression ratios (separated by backslash) of the applied
+     *          lossy compression steps. Only one value (and no backslash) if only
+     *          one step was performed. The parameter is ignored if isLossy is OFFalse.
+     *  @param  methods Methods (separated by backslash) of the applied
+     *          lossy compression steps. Only one value (and no backslash) if only
+     *          one step was performed. The parameter is ignored if isLossy is OFFalse.
+     *  @param  check If OFTrue, the data provided is checked for validity
+     *  @return EC_Normal if lossy compression info could be set, error code otherwise
+     */
+    virtual OFCondition setLossyImageCompression(const OFBool isLossy,
+                                                 const OFString& ratios  = "",
+                                                 const OFString& methods = "",
+                                                 const OFBool check      = OFTrue);
+
+    /** Set Isocenter Position
+     *  @param  values Value that should be set
+     *  @param  check If OFTrue, basic checks are performed whether the values are
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setISOCenterPosition(const OFVector<Float64>& values, const OFBool check = OFTrue);
+
+    /** Set Isocenter Position
+     *  @param  value Value that should be set
+     *  @param  check If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setISOCenterPosition(const OFString& value, const OFBool check = OFTrue);
+
+    /** Set Multi-Energy CT Acquisition
+     *  @param  value Value that should be set
+     *  @param  check If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setMultiEnergyCTAcquisition(const OFString& value, const OFBool check = OFTrue);
+
+    /** Set Pixel Presentation
+     *  @param  value Value that should be set
+     *  @param  check Ignored in current implementation (enum value is always checked for validity).
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setPixelPresentation(const EctTypes::E_PixelPresentation value, const OFBool check = OFTrue);
+
+    /** Set Volumetric Properties
+     *  @param  value Value that should be set
+     *  @param  check Ignored in current implementation (enum value is always checked for validity).
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setVolumetricProperties(const EctTypes::E_VolumetricProperties value,
+                                                const OFBool check = OFTrue);
+
+    /** Set Volume Based Calculation Technique
+     *  @param  value Value that should be set
+     *  @param  check If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setVolumeBasedCalculationTechnique(const OFString& value, const OFBool check = OFTrue);
+
+protected:
+    /** Protected default constructor. Library users should the factory create..()
+     *  method in order to create an object from scratch
+     */
+    template <typename ImagePixel>
+    EctEnhancedCT(OFin_place_type_t(ImagePixel));
+
+    /** Overwrites and publicly hides DcmIODImage::read()
+     *  @param  dataset The dataset to read from
+     *  @return EC_Normal if reading succeeded, error otherwise
+     */
+    virtual OFCondition read(DcmItem& dataset);
+
+    /** Overwrites and publicly hides DcmIODImage::write()
+     *  @param  dataset The dataset to write to
+     *  @return EC_Normal if writing succeeded, error otherwise
+     */
+    virtual OFCondition write(DcmItem& dataset);
+
+    /** Writes pixel data to item
+     *  @param  dataset The dataset to write to
+     *  @return EC_Normal if writing succeeded, error otherwise
+     */
+    virtual OFCondition writeGeneric(DcmItem& dataset);
+
+    /** Read Enhanced CT's generic (not directly pixel-data related) attributes from
+     *  DICOM dataset.
+     *  @param  dataset Reference to DICOM dataset to read from.
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition readGeneric(DcmItem& dataset);
+
+    /** General Image Module is not allowed in Enhanced CT, remove from public interface.
+     *  @return Reference to General Image Module
+     */
+    virtual IODGeneralImageModule& getGeneralImage()
+    {
+        return IODImage::getGeneralImage();
+    }
+
+private:
+    // Forward declarations (pixel type related Visitors)
+    struct SetImagePixelModuleVisitor;
+    struct ReadVisitor;
+    struct WriteVisitor;
+    struct WriteVisitorConcatenation;
+    struct GetFramesVisitor;
+
+    /// Synchronization Module
+    IODSynchronizationModule m_SynchronisationModule;
+
+    /// Denote whether Synchronization Module is enabled (OFTrue)
+    /// or ignored (OFFalse) on writing and checking.
+    OFBool m_SynchronisationModuleEnabled;
+
+    /// IODEnhancedEquipmentModule
+    IODEnhGeneralEquipmentModule m_EnhancedGeneralEquipmentModule;
+
+    /// Multi-frame Functional Groups module
+    IODMultiFrameFGModule m_FG;
+
+    /// Multi-frame Dimension Module
+    IODMultiframeDimensionModule m_DimensionModule;
+
+    /// Acquisition Context Module
+    IODAcquisitionContextModule m_AcquisitionContextModule;
+
+    /// Common Instance Reference Module
+    IODCommonInstanceReferenceModule m_CommonInstanceReferenceModule;
+
+    /// Binary frame data
+    OFVector<DcmIODTypes::Frame*> m_Frames;
+
+    /// Multi-frame Functional Groups high level interface
+    FGInterface m_FGInterface;
+
+    /* Image level information */
+
+    /// Image Type: (CS, VM 4, Type 1)
+    DcmCodeString m_ImageType;
+
+    /// Instance Number: (IS, VM 1, Type 1)
+    DcmIntegerString m_InstanceNumber;
+
+    /// Multi-Energy CT Acquisition: (CS VM 1, Type 3)
+    DcmCodeString m_MultiEnergyCTAcquisition;
+
+    /// Pixel Presentation: (CS, VM 1, Type 1)
+    DcmCodeString m_PixelPresentation;
+
+    /// Volumetric Properties: (CS, VM 1, Type 1)
+    DcmCodeString m_VolumetricProperties;
+
+    /// Volume Based Calculation Technique: (CS, VM 1, Type 1)
+    DcmCodeString m_VolumeBasedCalculationTechnique;
+
+    /// Acquisition Number: (IS, VM 1, Type 3)
+    DcmIntegerString m_AcquisitionNumber;
+
+    /// Acquisition DateTime: (DT, VM 1, Type 1C)
+    DcmDateTime m_AcquisitionDateTime;
+
+    /// Acquisition Duration: (FD, VM 1, Type 1C)
+    DcmFloatingPointDouble m_AcquisitionDuration;
+
+    /// Content Qualification: (CS, VM 1, Type 1C)
+    DcmCodeString m_ContentQualification;
+
+    /// Image Comments: (LT, VM 1, Type 3)
+    DcmLongText m_ImageComments;
+
+    /// Burned In Annotation: (CS, VM 1, Type 1C)
+    DcmCodeString m_BurnedInAnnotation;
+
+    /// Recognizable Visual Features: (CS, VM 1, Type 3)
+    DcmCodeString m_RecognizableVisualFeatures;
+
+    /// Lossy Image Compression: (CS, VM 1, Type 1C)
+    DcmCodeString m_LossyImageCompression;
+
+    /// Lossy Image Compression Ratio: (DS, VM 1, Type 1C)
+    DcmDecimalString m_LossyImageCompressionRatio;
+
+    /// Lossy Image Compression Method: (CS, VM 1, Type 1C)
+    DcmCodeString m_LossyImageCompressionMethod;
+
+    /// Presentation LUT Shape: (CS, VM 1, Type 1)
+    DcmCodeString m_PresentationLUTShape;
+
+    /// Isocenter Position: (DS, VM 3, Type 3)
+    DcmDecimalString m_IsoCenterPosition;
+
+    // --------------- private helper functions -------------------
+
+    /** Decompress the given dataset
+     *  @param  dset The dataset to be decompressed
+     *  @return EC_Normal if decompression worked (or dataset has already been
+     *  decompressed), IOD_EC_CannotDecompress otherwise
+     */
+    static OFCondition decompress(DcmDataset& dset);
+};
+
+#endif // DCMECT_ENHANCED_CT_H
diff --git a/dcmect/include/dcmtk/dcmect/types.h b/dcmect/include/dcmtk/dcmect/types.h
new file mode 100644 (file)
index 0000000..102bc75
--- /dev/null
@@ -0,0 +1,312 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmect
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing common Enhanced CT-specific types
+ *
+ */
+
+#ifndef DCMECT_TYPES_H
+#define DCMECT_TYPES_H
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmect/def.h"
+#include "dcmtk/dcmiod/iodmacro.h"
+#include "dcmtk/oflog/oflog.h"
+
+/*-----------------------*
+ * Logging               *
+ *-----------------------*/
+
+extern DCMTK_DCMECT_EXPORT OFLogger DCM_dcmectLogger;
+
+#define DCMECT_TRACE(msg) OFLOG_TRACE(DCM_dcmectLogger, msg)
+#define DCMECT_DEBUG(msg) OFLOG_DEBUG(DCM_dcmectLogger, msg)
+#define DCMECT_INFO(msg) OFLOG_INFO(DCM_dcmectLogger, msg)
+#define DCMECT_WARN(msg) OFLOG_WARN(DCM_dcmectLogger, msg)
+#define DCMECT_ERROR(msg) OFLOG_ERROR(DCM_dcmectLogger, msg)
+#define DCMECT_FATAL(msg) OFLOG_FATAL(DCM_dcmectLogger, msg)
+
+// include this file in doxygen documentation
+
+/** @file types.h
+ *  @brief type definitions, constants and helper classes for the dcmect module
+ */
+
+/*----------------------*
+ * Constant definitions *
+ *----------------------*/
+
+extern DCMTK_DCMECT_EXPORT const OFConditionConst ECT_InvalidDimensions;
+extern DCMTK_DCMECT_EXPORT const OFConditionConst ECT_InvalidAttributeValue;
+extern DCMTK_DCMECT_EXPORT const OFConditionConst ECT_InvalidPixelInfo;
+extern DCMTK_DCMECT_EXPORT const OFConditionConst ECT_InvalidPixelData;
+extern DCMTK_DCMECT_EXPORT const OFConditionConst ECT_NoPixelData;
+extern DCMTK_DCMECT_EXPORT const OFConditionConst ECT_InvalidSOPClass;
+
+/** General purpose class hiding global functions, constants and types in the
+ *  Enhanced CT context from the global namespace.
+ */
+class DCMTK_DCMECT_EXPORT EctTypes
+{
+
+public:
+    /// Enum containing the Enumerated Values for the first value of tag Image Type (0008,0008)
+    enum E_ImageType1
+    {
+        /// Denotes an empty attribute value (not permitted but may be found when reading
+        /// an invalid object)
+        E_ImageType1_Empty,
+        /// Denotes any invalid attribute value (not permitted but may be found when reading
+        /// an invalid object)
+        E_ImageType1_Invalid,
+        /// Reflects the value "ORIGINAL"
+        E_ImageType1_Original,
+        /// Reflects the value "DERIVED"
+        E_ImageType1_Derived,
+        /// Reflects the value "MIXED"
+        E_ImageType1_Mixed
+    };
+
+    /// Enum containing the Enumerated Values for the 2nd value of tag Image Type (0008,0008)
+    enum E_ImageType2
+    {
+        /// Denotes an empty attribute value (not permitted but may be found when reading
+        /// an invalid object)
+        E_ImageType2_Empty,
+        /// Denotes any invalid attribute value (not permitted but may be found when reading
+        /// an invalid object)
+        E_ImageType2_Invalid,
+        /// Reflects the value "PRIMARY" which is the only valid value permitted
+        E_ImageType2_Primary
+    };
+
+    /// Defined Term "ANGIO" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_Angio;
+    /// Defined Term "CARDIAC" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_Cardiac;
+    /// Defined Term "CARDIAC_GATED" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_CardiacGated;
+    /// Defined Term "CARDRESP_GATED" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_CardRespGated;
+    /// Defined Term "DYNAMIC" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_Dynamic;
+    /// Defined Term "FLUOROSCOPY" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_Fluoroscopy;
+    /// Defined Term "LOCALIZER" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_Localizer;
+    /// Defined Term "MOTION" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_Motion;
+    /// Defined Term "PERFUSION" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_Perfusion;
+    /// Defined Term "PRE_CONTRAST" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_PreContrast;
+    /// Defined Term "POST_CONTRAST" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_PostContrast;
+    /// Defined Term "RESP_GATED" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_RespGated;
+    /// Defined Term "REST" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_Rest;
+    /// Defined Term "STATIC" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_Static;
+    /// Defined Term "STRESS" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_Stress;
+    /// Defined Term "VOLUME" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_Volume;
+    /// Defined Term "NON_PARALLEL" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_NonParallel;
+    /// Defined Term "WHOLE_BODY" for 3rd value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType3_WholeBody;
+
+    /// Defined Term "ADDITION" for 4th value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType4_Addition;
+    /// Defined Term "DIVISION" for 4th value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType4_Division;
+    /// Defined Term "MASKED" for 4th value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType4_Masked;
+    /// Defined Term "MAXIMUM" for 4th value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType4_Maximum;
+    /// Defined Term "MEAN" for 4th value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType4_Mean;
+    /// Defined Term "MINIMUM" for 4th value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType4_Minimum;
+    /// Defined Term "MULTIPLICATION" for 4th value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType4_Multiplication;
+    /// Defined Term "RESAMPLED" for 4th value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType4_Resampled;
+    /// Defined Term "STD_DEVIATION" for 4th value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType4_Std_Deviation;
+    /// Defined Term "SUBTRACTION" for 4th value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType4_Subtraction;
+    /// Defined Term "NONE" for 4th value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType4_None;
+    /// Defined Term "QUANTITY" for 4th value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType4_Quantity;
+    /// Defined Term "MIXED" for 4th value of tag Image Type (0008,0008)
+    static const OFString DT_ImageType4_Mixed;
+
+    /// Enum containing the Enumerated Values of tag Content Qualification (0018,9004)
+    enum E_ContentQualification
+    {
+        /// Denotes an empty attribute value (not permitted but may be found when reading
+        /// an invalid object)
+        E_ContentQuali_Empty,
+        /// Denotes an invalid attribute value (not permitted but may be found when reading
+        /// an invalid object)
+        E_ContentQuali_Invalid,
+        /// Reflects the value "PRODUCT" which is the only valid value permitted
+        E_ContQuali_Product,
+        /// Reflects the value "RESEARCH" which is the only valid value permitted
+        E_ContQuali_Research,
+        /// Reflects the value "SERVICE" which is the only valid value permitted
+        E_ContQuali_Service
+    };
+
+    /// Enum containing the Enumerated Values of tag Burned In Annotation (0028,0301)
+    enum E_BurnedInAnnotation
+    {
+        /// Denotes an empty attribute value (not permitted but may be found when reading
+        /// an invalid object)
+        E_BurnedInAnno_Empty,
+        /// Denotes an invalid attribute value (not permitted but may be found when reading
+        /// an invalid object)
+        E_BurnedInAnno_Invalid,
+        /// Reflects the value "NO" which is the only valid value permitted
+        E_BurnedInAnno_No
+    };
+
+    /// Enum containing the Enumerated Values of tag Recognizable Visual Features (0028,0302)
+    enum E_RecognizableVisualFeatures
+    {
+        /// Denotes an empty attribute value (not permitted but may be found when reading
+        /// an invalid object)
+        E_RecoVisFeatures_Empty,
+        /// Denotes an invalid attribute value (not permitted but may be found when reading
+        /// an invalid object)
+        E_RecoVisFeatures_Invalid,
+        /// Reflects the value "YES"
+        E_RecoVisFeatures_Yes,
+        /// Reflects the value "NO"
+        E_RecoVisFeatures_No
+    };
+
+    /// Enum containing the Enumerated Values of tag Pixel Presentation (0008,9205)
+    enum E_PixelPresentation
+    {
+        /// Denotes an empty attribute value (not permitted but may be found when reading
+        /// an invalid object)
+        E_PixelPres_Empty,
+        /// Denotes an invalid attribute value (not permitted but may be found when reading
+        /// an invalid object)
+        E_PixelPres_Invalid,
+        /// Reflects the value "COLOR"
+        E_PixelPres_Color,
+        /// Reflects the value "MONOCHROME"
+        E_PixelPres_Monochrome,
+        /// Reflects the value "MIXED"
+        E_PixelPres_Mixed,
+        /// Reflects the value "TRUE_COLOR"
+        E_PixelPres_TrueColor
+    };
+
+    /// Enum containing the Enumerated Values of tag Volumetric Properties (0008,9206)
+    enum E_VolumetricProperties
+    {
+        /// Denotes an empty attribute value (not permitted but may be found when reading
+        /// an invalid object)
+        E_VolProps_Empty,
+        /// Denotes an invalid attribute value (not permitted but may be found when reading
+        /// an invalid object)
+        E_VolProps_Invalid,
+        /// Reflects the value "VOLUME"
+        E_VolProps_Volume,
+        /// Reflects the value "SAMPLED"
+        E_VolProps_Sampled,
+        /// Reflects the value "DISTORTED"
+        E_VolProps_Distorted,
+        /// Reflects the value "MIXED"
+        E_VolProps_Mixed
+    };
+
+    /// Defined Term "MAX_IP" for tag Volume Based Calculation Technique
+    static const OFString DT_VolBasedCalcTechnique_MaxIp;
+    /// Defined Term "MIN_IP" for tag Volume Based Calculation Technique
+    static const OFString DT_VolBasedCalcTechnique_MinIp;
+    /// Defined Term "VOLUME_RENDER" for tag Volume Based Calculation Technique
+    static const OFString DT_VolBasedCalcTechnique_VolumeRender;
+    /// Defined Term "SURFACE_RENDER" for tag Volume Based Calculation Technique
+    static const OFString DT_VolBasedCalcTechnique_SurfaceRender;
+    /// Defined Term "MPR" for tag Volume Based Calculation Technique
+    static const OFString DT_VolBasedCalcTechnique_Mpr;
+    /// Defined Term "CURVED_MPR" for tag Volume Based Calculation Technique
+    static const OFString DT_VolBasedCalcTechnique_CurvedMpr;
+    /// Defined Term "NONE" for tag Volume Based Calculation Technique
+    static const OFString DT_VolBasedCalcTechnique_None;
+    /// Defined Term "MIXED" for tag Volume Based Calculation Technique
+    static const OFString DT_VolBasedCalcTechnique_Mixed;
+
+    /** Returns related string for given enum value. Returns empty string for
+     *  invalid or empty values.
+     *  @param  value The enum value
+     *  @return The related string value
+     */
+    static OFString imageType1ToStr(const E_ImageType1 value);
+
+    /** Returns related string for given enum value. Returns empty string for
+     *  invalid or empty values.
+     *  @param  value The enum value
+     *  @return The related string value
+     */
+    static OFString imageType2ToStr(const E_ImageType2 value);
+
+    /** Returns related string for given enum value. Returns empty string for
+     *  invalid or empty values.
+     *  @param  value The enum value
+     *  @return The related string value
+     */
+    static OFString contentQualiToStr(const E_ContentQualification value);
+
+    /** Returns related string for given enum value. Returns empty string for
+     *  invalid or empty values.
+     *  @param  value The enum value
+     *  @return The related string value
+     */
+    static OFString burnedAnnoToStr(const E_BurnedInAnnotation value);
+
+    /** Returns related string for given enum value. Returns empty string for
+     *  invalid or empty values.
+     *  @param  value The enum value
+     *  @return The related string value
+     */
+    static OFString pixelPresToStr(const E_PixelPresentation value);
+
+    /** Returns related string for given enum value. Returns empty string for
+     *  invalid or empty values.
+     *  @param  value The enum value
+     *  @return The related string value
+     */
+    static OFString volPropsToStr(const E_VolumetricProperties value);
+
+    /** Returns related string for given enum value. Returns empty string for
+     *  invalid or empty values.
+     *  @param  value The enum value
+     *  @return The related string value
+     */
+    static OFString recoVisFeaturesToStr(const E_RecognizableVisualFeatures value);
+};
+
+#endif // DCMECT_TYPES_H
diff --git a/dcmect/libsrc/CMakeLists.txt b/dcmect/libsrc/CMakeLists.txt
new file mode 100644 (file)
index 0000000..87c450d
--- /dev/null
@@ -0,0 +1,4 @@
+# create library from source files
+DCMTK_ADD_LIBRARY(dcmect enhanced_ct types)
+
+DCMTK_TARGET_LINK_MODULES(dcmect dcmfg dcmiod dcmdata ofstd oflog)
diff --git a/dcmect/libsrc/Makefile.dep b/dcmect/libsrc/Makefile.dep
new file mode 100644 (file)
index 0000000..e4f081d
--- /dev/null
@@ -0,0 +1,284 @@
+enhanced_ct.o: enhanced_ct.cc ../include/dcmtk/dcmect/enhanced_ct.h \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmect/def.h ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../include/dcmtk/dcmect/types.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fginterface.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fg.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgbase.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodimage.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodcommn.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modpatient.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modpatientstudy.h \
+ ../../ofstd/include/dcmtk/ofstd/ofoption.h \
+ ../../ofstd/include/dcmtk/ofstd/ofalign.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modsopcommon.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralimage.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixelvariant.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixelbase.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvriant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/variant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/helpers.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdiag.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/push.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/cnvrsn.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/vsprfw.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/pop.def \
+ ../../dcmiod/include/dcmtk/dcmiod/modacquisitioncontext.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modenhequipment.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixel.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modmultiframedimension.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modmultiframefg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modsynchronisation.h \
+ ../../dcmfg/include/dcmtk/dcmfg/concatenationcreator.h \
+ ../../dcmfg/include/dcmtk/dcmfg/concatenationloader.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../ofstd/include/dcmtk/ofstd/oftuple.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/mmtag.def \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefrd.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuple.h
+types.o: types.cc ../include/dcmtk/dcmect/types.h \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmect/def.h ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modbase.h
diff --git a/dcmect/libsrc/Makefile.in b/dcmect/libsrc/Makefile.in
new file mode 100644 (file)
index 0000000..c97447c
--- /dev/null
@@ -0,0 +1,56 @@
+#
+#      Makefile for dcmect/libsrc
+#
+
+@SET_MAKE@
+
+SHELL = /bin/sh
+VPATH = @srcdir@:@top_srcdir@/include:@top_srcdir@/@configdir@/include
+srcdir = @srcdir@
+top_srcdir = @top_srcdir@
+configdir = @top_srcdir@/@configdir@
+
+include $(configdir)/@common_makefile@
+
+ofstddir = $(top_srcdir)/../ofstd
+oflogdir = $(top_srcdir)/../oflog
+dcmdatadir = $(top_srcdir)/../dcmdata
+dcmioddir = $(top_srcdir)/../dcmiod
+dcmfgdir = $(top_srcdir)/../dcmfg
+
+LOCALINCLUDES = -I$(ofstddir)/include -I$(oflogdir)/include \
+       -I$(dcmdatadir)/include -I$(dcmioddir)/include \
+       -I$(dcmfgdir)/include
+
+LOCALDEFS =
+
+objs = enhanced_ct.o types.o
+
+
+library = libdcmect.$(LIBEXT)
+
+
+all: $(library)
+
+install: $(library)
+       $(configdir)/mkinstalldirs $(DESTDIR)$(libdir)
+       $(INSTALL_DATA) $(library) $(DESTDIR)$(libdir)/$(library)
+       $(RANLIB) $(DESTDIR)$(libdir)/$(library)
+
+
+$(library): $(objs)
+       $(AR) $(ARFLAGS) $@ $(objs)
+       $(RANLIB) $@
+
+
+clean:
+       rm -f $(objs) $(library) $(TRASH)
+
+distclean:
+       rm -f $(objs) $(library) $(DISTTRASH)
+
+
+dependencies:
+       $(CXX) -MM $(defines) $(includes) $(CPPFLAGS) $(CXXFLAGS) *.cc  > $(DEP)
+
+include $(DEP)
diff --git a/dcmect/libsrc/enhanced_ct.cc b/dcmect/libsrc/enhanced_ct.cc
new file mode 100644 (file)
index 0000000..007cb88
--- /dev/null
@@ -0,0 +1,1225 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class representing a Enhanced CT object
+ *
+ */
+#include "dcmtk/dcmect/enhanced_ct.h"
+#include "dcmtk/config/osconfig.h"
+#include "dcmtk/dcmdata/dcuid.h"
+#include "dcmtk/dcmect/types.h"
+#include "dcmtk/dcmfg/concatenationcreator.h"
+#include "dcmtk/dcmfg/concatenationloader.h"
+#include "dcmtk/dcmiod/iodutil.h"
+#include "dcmtk/dcmiod/modimagepixel.h"
+
+struct EctEnhancedCT::SetImagePixelModuleVisitor
+{
+    SetImagePixelModuleVisitor(const Uint16 r, const Uint16 c)
+        : rows(r)
+        , cols(c)
+    {
+    }
+
+    template <typename T>
+    OFCondition operator()(T& t)
+    {
+        if ((rows == 0) || (cols == 0))
+        {
+            DCMECT_ERROR("Rows/Cols must be non-zero but are : " << rows << "/" << cols);
+            return ECT_InvalidDimensions;
+        }
+
+        t.setRows(rows);
+        t.setColumns(cols);
+        t.setBitsAllocated(16);
+        t.setBitsStored(16);
+        t.setHighBit(15);
+        t.setSamplesPerPixel(1);
+        t.setPhotometricInterpretation("MONOCHROME2");
+        t.setPixelRepresentation(OFis_signed<T>::value ? 1 : 0);
+
+        return EC_Normal;
+    }
+
+    // Members
+    const Uint16 rows;
+    const Uint16 cols;
+};
+
+// ----------------------------------------------------------------------------
+// Class WriteVisitor:
+// Class for adding DICOM pixel data bulk element based on type pixel data type
+// ----------------------------------------------------------------------------
+
+// Generic implementation, template specialization is done in inner
+// DcmElementOf class
+struct EctEnhancedCT::WriteVisitor
+{
+    // Inner class that implements the specializations for different
+    // pixel data types
+    // template <typename T> class DcmElementOf;
+
+    // Constructor, sets parameters the visitor works on in operator()
+    WriteVisitor(DcmItem& i, EctEnhancedCT& m)
+        : m_Item(i)
+        , m_CT(m)
+    {
+        // Nothing else to do
+    }
+
+    //
+    OFCondition operator()(OFmonostate)
+    {
+        DCMECT_ERROR("Could not write pixel data: Invalid pixel data type, only 16 bit integer is handled");
+        return ECT_NoPixelData;
+    }
+
+    template <typename ImagePixel>
+    OFCondition operator()(ImagePixel& pixel)
+    {
+        // Avoid compiler warning about unused parameter "pixel"
+        (void)pixel;
+        // Input data is checked before
+        Uint16 rows = 0;
+        Uint16 cols = 0;
+        m_CT.getRows(rows);
+        m_CT.getColumns(cols);
+        const size_t numFrames      = m_CT.m_Frames.size();
+        const size_t numBytesFrame  = m_CT.m_Frames[0]->length;
+        const size_t numPixelsFrame = rows * cols;
+        // Creates the correct pixel data element, based on the image pixel module used.
+        DcmPixelData* pixData = new DcmPixelData(DCM_PixelData);
+        OFCondition result;
+        if (pixData)
+        {
+            pixData->setVR(EVR_OW);
+            Uint16* ptr          = NULL;
+            size_t numBytesTotal = numBytesFrame * numFrames / 2;
+            if (numBytesTotal <= 4294967294UL)
+            {
+                result = pixData->createUint16Array(OFstatic_cast(Uint32, numBytesTotal), ptr);
+                // copy all frames into CT's frame structure
+                if (ptr)
+                {
+                    for (size_t f = 0; f < numFrames; ++f)
+                    {
+                        memcpy(ptr, m_CT.m_Frames[f]->pixData, numBytesFrame);
+                        ptr += numPixelsFrame;
+                    }
+                    return m_Item.insert(pixData);
+                }
+            }
+            else
+            {
+                result = FG_EC_PixelDataTooLarge;
+                delete pixData;
+            }
+        }
+        return result;
+    }
+
+    // Members, i.e. parameters to operator()
+    DcmItem& m_Item;
+    EctEnhancedCT& m_CT;
+};
+
+// Generic implementation, template specialization is done in inner
+// DcmElementOf class
+struct EctEnhancedCT::WriteVisitorConcatenation
+{
+    // Inner class that implements the writing to Concatentions via ConcatenationCreator class
+
+    // Constructor, sets parameters the visitor works on in operator()
+    WriteVisitorConcatenation(EctEnhancedCT& m, Uint8*& pixData, size_t& pixDataLength)
+        : m_CT(m)
+        , m_pixData(pixData)
+        , m_pixDataLength(pixDataLength)
+    {
+        // Nothing else to do
+    }
+
+    //
+    OFCondition operator()(OFmonostate)
+    {
+        DCMECT_ERROR("Could not write pixel data: Invalid pixel data type, only 16 bit integer is handled");
+        return ECT_NoPixelData;
+    }
+
+    template <typename ImagePixel>
+    OFCondition operator()(ImagePixel& pixel)
+    {
+        // Avoid compiler warning about unused parameter "pixel"
+        (void)pixel;
+        // Input data is checked before
+        Uint16 rows = 0;
+        Uint16 cols = 0;
+        m_CT.getRows(rows);
+        m_CT.getColumns(cols);
+        const size_t numFrames     = m_CT.m_Frames.size();
+        const size_t numBytesFrame = m_CT.m_Frames[0]->length;
+        // Creates the correct pixel data element, based on the image pixel module used.
+        m_pixDataLength = numBytesFrame * numFrames;
+        m_pixData       = new Uint8[m_pixDataLength];
+        if (m_pixData)
+        {
+            Uint8* ptr = m_pixData;
+            // copy all frames into CT's frame structure
+            if (ptr)
+            {
+                for (size_t f = 0; f < numFrames; ++f)
+                {
+                    memcpy(ptr, m_CT.m_Frames[f]->pixData, numBytesFrame);
+                    ptr += numBytesFrame;
+                }
+                return EC_Normal;
+            }
+        }
+        m_pixData       = OFnullptr;
+        m_pixDataLength = 0;
+        return EC_MemoryExhausted;
+    }
+
+    // Members, i.e. parameters to operator()
+    EctEnhancedCT& m_CT;
+    Uint8*& m_pixData;
+    size_t& m_pixDataLength;
+};
+
+struct EctEnhancedCT::ReadVisitor
+{
+    // Inner class that implements the specializations for different
+    // pixel data types
+    template <typename T>
+    class DcmElementOf;
+
+    ReadVisitor(DcmItem& srcItem, EctEnhancedCT& m, const OFBool readPixelData = OFTrue)
+        : m_Item(srcItem)
+        , m_CT(m)
+        , m_readPixelData(readPixelData)
+    {
+        // Nothing to do
+    }
+
+    OFCondition operator()(OFmonostate)
+    {
+        return ECT_InvalidPixelData;
+    }
+
+    template <typename ImagePixel>
+    OFCondition operator()(ImagePixel& pixel)
+    {
+        m_CT.readGeneric(m_Item);
+        OFCondition result;
+        Uint16 rows, cols;
+        Uint32 numFrames;
+        size_t numBytesFrame = 0;
+        rows = cols = 0;
+        m_CT.getRows(rows);
+        m_CT.getColumns(cols);
+        numFrames = DcmIODUtil::limitMaxFrames(
+            m_CT.getFunctionalGroups().getNumberOfFrames(),
+            "Functional groups implicate more than 2147483647 frames, only 2147483647 will be used");
+        if (!rows || !cols || !numFrames)
+        {
+            DCMECT_ERROR("Rows (" << rows << "), Columns (" << cols << ") and Number of Frames (" << numFrames
+                                  << ") must not be 0");
+            return ECT_InvalidPixelInfo;
+        }
+        numBytesFrame = OFstatic_cast(size_t, rows) * cols * sizeof(typename ImagePixel::value_type);
+        if (m_readPixelData)
+        {
+            result = readSpecific(pixel, numFrames, numBytesFrame);
+        }
+        return result;
+    }
+
+    template <typename T>
+    OFCondition readSpecific(IODImagePixelModule<T>& p, const Uint32 numFrames, const size_t numBytesFrame)
+    {
+        // Avoid compiler warning about unused parameter
+        (void)p;
+        unsigned long numTotalWords = 0;
+        const Uint16* pixData       = NULL;
+        if (m_Item.findAndGetUint16Array(DCM_PixelData, pixData, &numTotalWords).good())
+        {
+            if (numTotalWords == numBytesFrame * numFrames / 2 /* we compare to num words not num bytes */)
+            {
+                for (Uint32 n = 0; n < numFrames; n++)
+                {
+                    DcmIODTypes::Frame* f = new DcmIODTypes::Frame;
+                    if (f)
+                    {
+                        f->length  = numBytesFrame;
+                        f->pixData = new Uint8[f->length];
+                        memcpy(f->pixData, pixData + n * numBytesFrame / 2, numBytesFrame);
+                        m_CT.m_Frames.push_back(f);
+                    }
+                    else
+                    {
+                        return EC_MemoryExhausted;
+                    }
+                }
+            }
+            else
+            {
+                DCMECT_ERROR("Invalid number of pixels: Expected " << numBytesFrame * numFrames / 2
+                                                                   << " pixels but Pixel Data has " << numTotalWords
+                                                                   << " pixels");
+                return ECT_InvalidPixelInfo;
+            }
+        }
+        else
+        {
+            DCMECT_ERROR("No Pixel Data element found");
+            return ECT_NoPixelData;
+        }
+        return EC_Normal;
+    }
+
+    // Members, i.e. parameters to operator()
+    DcmItem& m_Item;
+    EctEnhancedCT& m_CT;
+    OFBool m_readPixelData;
+};
+
+template <typename PixelType>
+EctEnhancedCT::Frames<PixelType>::Frames(EctEnhancedCT& ct)
+    : m_CT(ct)
+{
+}
+
+template <typename PixelType>
+OFCondition EctEnhancedCT::Frames<PixelType>::addFrame(PixelType* data,
+                                                       const size_t numPixels,
+                                                       const OFVector<FGBase*>& perFrameInformation)
+{
+    OFCondition result;
+    if (data && numPixels)
+    {
+        if (!perFrameInformation.empty())
+        {
+            OFunique_ptr<DcmIODTypes::Frame> f(new DcmIODTypes::Frame);
+            if (f)
+            {
+                f->length  = numPixels * sizeof(PixelType);
+                f->pixData = new Uint8[f->length];
+                memcpy(f->pixData, data, f->length);
+                m_CT.m_Frames.push_back(f.release());
+                OFVector<FGBase*>::const_iterator fg = perFrameInformation.begin();
+                while (result.good() && (fg != perFrameInformation.end()))
+                {
+                    result = m_CT.m_FGInterface.addPerFrame(OFstatic_cast(Uint32, m_CT.m_Frames.size()), **fg);
+                    if (result.bad())
+                    {
+                        DCMECT_ERROR(
+                            "Could not add functional group: " << DcmFGTypes::FGType2OFString((*fg)->getType()));
+                        break;
+                    }
+                    ++fg;
+                }
+            }
+        }
+    }
+    // Clean up if necessary
+    if (result.bad())
+        m_CT.m_FGInterface.deleteFrame(OFstatic_cast(Uint32, m_CT.m_Frames.size()));
+    return result;
+}
+
+template <typename PixelType>
+PixelType* EctEnhancedCT::Frames<PixelType>::getFrame(const size_t frameNumber)
+{
+    if (frameNumber < m_CT.m_Frames.size())
+    {
+        return (PixelType*)(m_CT.m_Frames[frameNumber]->pixData);
+    }
+    return NULL;
+}
+
+// Helper "class" that returns Frames offering API to the pixel's frame bulk
+// data by offering the dedicated data type, e.g. Float32 instead of the
+// internally stored generic Uint8 array.
+//
+struct EctEnhancedCT::GetFramesVisitor
+{
+    GetFramesVisitor(EctEnhancedCT& ct)
+        : m_CT(ct)
+    {
+    }
+
+    OFCondition operator()(OFmonostate)
+    {
+        return ECT_InvalidPixelData;
+    }
+
+    template <typename ImagePixel>
+    Frames<OFTypename ImagePixel::value_type> operator()(ImagePixel&)
+    {
+        return Frames<OFTypename ImagePixel::value_type>(m_CT);
+    }
+
+    EctEnhancedCT& m_CT;
+};
+
+// default constructor (protected, instance creation via create() function)
+template <typename ImagePixel>
+EctEnhancedCT::EctEnhancedCT(OFin_place_type_t(ImagePixel))
+    : IODImage(OFin_place<ImagePixel>)
+    , m_SynchronisationModule()
+    , m_SynchronisationModuleEnabled(OFFalse)
+    , m_EnhancedGeneralEquipmentModule()
+    , m_FG()
+    , m_DimensionModule()
+    , m_AcquisitionContextModule()
+    , m_CommonInstanceReferenceModule()
+    , m_Frames()
+    , m_FGInterface()
+    , m_ImageType(DCM_ImageType)
+    , m_InstanceNumber(DCM_InstanceNumber)
+    , m_MultiEnergyCTAcquisition(DCM_MultienergyCTAcquisition)
+    , m_PixelPresentation(DCM_PixelPresentation)
+    , m_VolumetricProperties(DCM_VolumetricProperties)
+    , m_VolumeBasedCalculationTechnique(DCM_VolumeBasedCalculationTechnique)
+    , m_AcquisitionNumber(DCM_AcquisitionNumber)
+    , m_AcquisitionDateTime(DCM_AcquisitionDateTime)
+    , m_AcquisitionDuration(DCM_AcquisitionDuration)
+    , m_ContentQualification(DCM_ContentQualification)
+    , m_ImageComments(DCM_ImageComments)
+    , m_BurnedInAnnotation(DCM_BurnedInAnnotation)
+    , m_RecognizableVisualFeatures(DCM_RecognizableVisualFeatures)
+    , m_LossyImageCompression(DCM_LossyImageCompression)
+    , m_LossyImageCompressionRatio(DCM_LossyImageCompressionRatio)
+    , m_LossyImageCompressionMethod(DCM_LossyImageCompressionMethod)
+    , m_PresentationLUTShape(DCM_PresentationLUTShape)
+    , m_IsoCenterPosition(DCM_IsocenterPosition)
+{
+    setGeneralImageModuleEnabled(OFFalse);
+}
+
+// ------------------ Constructors, Loading, Saving -----------------------
+
+EctEnhancedCT::~EctEnhancedCT()
+{
+    DcmIODUtil::freeContainer(m_Frames);
+}
+
+OFCondition EctEnhancedCT::loadFile(const OFString& filename, EctEnhancedCT*& ct)
+{
+    DcmFileFormat dcmff;
+    OFCondition cond = dcmff.loadFile(filename.c_str());
+    if (cond.good())
+    {
+        cond = loadDataset(*(dcmff.getDataset()), ct);
+    }
+    return cond;
+}
+
+OFCondition EctEnhancedCT::loadDataset(DcmDataset& dataset, EctEnhancedCT*& ct)
+{
+    OFCondition result;
+    OFString sopClass;
+    if (dataset.findAndGetOFStringArray(DCM_SOPClassUID, sopClass).good())
+    {
+        if (sopClass == UID_EnhancedCTImageStorage)
+        {
+            result = decompress(dataset);
+            if (result.good())
+            {
+
+                DcmElement* elem = NULL;
+                if (dataset.findAndGetElement(DCM_PixelData, elem).good())
+                {
+                    Uint16 pr = 0;
+                    if (dataset.findAndGetUint16(DCM_PixelRepresentation, pr).good())
+                    {
+                        if (pr == 0)
+                        {
+                            ct = new EctEnhancedCT(OFin_place<IODImagePixelModule<Uint16> >);
+                        }
+                        else
+                        {
+                            ct = new EctEnhancedCT(OFin_place<IODImagePixelModule<Sint16> >);
+                        }
+                    }
+                    else
+                    {
+                        DCMECT_WARN("Pixel Data element found but no Pixel Presentation set, assuming 16 bit unsigned "
+                                    "integer data");
+                        ct = new EctEnhancedCT(OFin_place<IODImagePixelModule<Uint16> >);
+                    }
+                }
+                else
+                {
+                    return ECT_NoPixelData;
+                }
+                if (ct == NULL)
+                {
+                    return EC_MemoryExhausted;
+                }
+            }
+            else
+            {
+                return result;
+            }
+        }
+        else
+        {
+            DCMECT_ERROR("Invalid SOP Class: "
+                         << sopClass << ", only Enhanced CT Image Storage (1.2.840.10008.5.1.4.1.1.2.1​) supported");
+            return ECT_InvalidSOPClass;
+        }
+    }
+    result = OFvisit<OFCondition>(ReadVisitor(dataset, *ct), ct->getImagePixel());
+    if (result.bad())
+    {
+        delete ct;
+        ct = NULL;
+    }
+    return result;
+}
+
+OFCondition
+EctEnhancedCT::loadConcatenation(ConcatenationLoader& cl, const OFString& concatenationUID, EctEnhancedCT*& ct)
+{
+
+    DcmDataset dset;
+    ct = NULL;
+    OFVector<DcmIODTypes::Frame*> frames;
+    OFCondition result = cl.load(concatenationUID, &dset, frames);
+    if (result.good())
+    {
+        Uint16 pr = 0;
+        if (dset.findAndGetUint16(DCM_PixelRepresentation, pr).good())
+        {
+            if (pr == 0)
+            {
+                ct = new EctEnhancedCT(OFin_place<IODImagePixelModule<Uint16> >);
+            }
+            else
+            {
+                ct = new EctEnhancedCT(OFin_place<IODImagePixelModule<Sint16> >);
+            }
+        }
+        else
+        {
+            DCMECT_WARN("No Pixel Presentation set, assuming 16 bit unsigned "
+                        "integer data");
+            ct = new EctEnhancedCT(OFin_place<IODImagePixelModule<Uint16> >);
+        }
+        result
+            = OFvisit<OFCondition>(ReadVisitor(dset, *ct, OFFalse /* do not read pixel data */), ct->getImagePixel());
+        if (result.good())
+        {
+            ct->m_Frames = frames;
+        }
+        if (result.bad())
+        {
+            delete ct;
+            ct = NULL;
+        }
+    }
+    return result;
+}
+
+OFCondition EctEnhancedCT::saveFile(const OFString& filename, const E_TransferSyntax writeXfer)
+{
+    DcmFileFormat dcmff;
+    OFCondition result;
+    if ((result = write(*dcmff.getDataset())).good())
+        result = dcmff.saveFile(filename.c_str(), writeXfer);
+    if (result.bad())
+        DCMECT_ERROR("Cannot save Enhanced CT object to file " << filename << ": " << result.text());
+    return result;
+}
+
+OFCondition EctEnhancedCT::writeDataset(DcmItem& dataset)
+{
+    return write(dataset);
+}
+
+void EctEnhancedCT::setCheckFGOnWrite(const OFBool doCheck)
+{
+    m_FGInterface.setCheckOnWrite(doCheck);
+}
+
+OFBool EctEnhancedCT::getCheckFGOnWrite()
+{
+    return m_FGInterface.getCheckOnWrite();
+}
+
+// ------------------ Creation -----------------------
+
+OFCondition EctEnhancedCT::create(EctEnhancedCT*& ct,
+                                  const Uint16 rows,
+                                  const Uint16 columns,
+                                  const OFBool signedPixelData,
+                                  const EctTypes::E_ImageType1 imageType1,
+                                  const OFString& imageType3,
+                                  const OFString& imageType4,
+                                  const OFString& instanceNumber,
+                                  const EctTypes::E_ContentQualification contentQualification,
+                                  const EctTypes::E_PixelPresentation pixelPresentation,
+                                  const EctTypes::E_VolumetricProperties volumetricProperties,
+                                  const OFString& volumeBasedCalculationTechnique,
+                                  const IODEnhGeneralEquipmentModule::EquipmentInfo& equipmentInfo,
+                                  const OFString& acquisitionDateTime,
+                                  const Float64& acquisitionDuration)
+{
+    ct = OFnullptr;
+    OFCondition status;
+    if (!signedPixelData)
+    {
+        ct = new EctEnhancedCT(OFin_place<IODImagePixelModule<Uint16> >);
+        if (ct)
+            status
+                = SetImagePixelModuleVisitor(rows, columns)(*OFget<IODImagePixelModule<Uint16> >(&ct->getImagePixel()));
+        else
+            status = EC_MemoryExhausted;
+    }
+    else
+    {
+        ct = new EctEnhancedCT(OFin_place<IODImagePixelModule<Sint16> >);
+        if (ct)
+            status
+                = SetImagePixelModuleVisitor(rows, columns)(*OFget<IODImagePixelModule<Sint16> >(&ct->getImagePixel()));
+        else
+            status = EC_MemoryExhausted;
+    }
+    if (status.bad())
+        return status;
+
+    if (status.good())
+        status = ct->getSOPCommon().setSOPClassUID(UID_EnhancedCTImageStorage);
+
+    if (status.good())
+        status = ct->setImageType(EctTypes::imageType1ToStr(imageType1) + "\\"
+                                  + EctTypes::imageType2ToStr(EctTypes::E_ImageType2_Primary) + "\\" + imageType3 + "\\"
+                                  + imageType4);
+
+    if (status.good())
+        status = ct->getIODMultiFrameFGModule().setInstanceNumber(instanceNumber);
+    if (status.good())
+        status = ct->setContentQualification(contentQualification);
+    if (status.good())
+        status = ct->setPixelPresentation(pixelPresentation);
+    if (status.good())
+        status = ct->setVolumetricProperties(volumetricProperties);
+    if (status.good())
+        status = ct->setVolumeBasedCalculationTechnique(volumeBasedCalculationTechnique);
+    if (status.good())
+        status = ct->setLossyImageCompression(OFFalse);
+    if (status.good())
+        status = ct->getIODEnhGeneralEquipmentModule().set(equipmentInfo);
+    if (status.good() && (!acquisitionDateTime.empty()))
+        status = ct->setAcquisitionDateTime(acquisitionDateTime);
+    if (status.good() && (acquisitionDuration >= 0))
+        status = ct->setAcquisitionDuration(acquisitionDuration);
+    if (status.good())
+        status = ct->m_BurnedInAnnotation.putOFStringArray("NO");
+
+    if (status.good())
+        status = DcmIODUtil::setContentDateAndTimeNow(ct->getIODMultiFrameFGModule());
+
+    return status;
+}
+
+// ------------------ Access -----------------------
+
+OFBool EctEnhancedCT::check(const OFBool checkFGStructure)
+{
+    if (m_Frames.size() == 0)
+    {
+        DCMECT_ERROR("No frame data available");
+        return OFFalse;
+    }
+
+    if (checkFGStructure)
+    {
+        if (!m_FGInterface.check())
+            return OFFalse;
+    }
+
+    return OFTrue;
+}
+
+FGInterface& EctEnhancedCT::getFunctionalGroups()
+{
+    return m_FGInterface;
+}
+
+IODMultiFrameFGModule::ConcatenationInfo& EctEnhancedCT::getConcatenationInfo()
+{
+    return m_FG.getConcatenationInfo();
+}
+
+size_t EctEnhancedCT::getNumberOfFrames() const
+{
+    return OFconst_cast(EctEnhancedCT*, this)->m_FGInterface.getNumberOfFrames();
+}
+
+// ------------------ Access -----------------------
+
+OFCondition EctEnhancedCT::addForAllFrames(const FGBase& group)
+{
+    return m_FGInterface.addShared(group);
+}
+
+IODMultiframeDimensionModule& EctEnhancedCT::getDimensions()
+{
+    return m_DimensionModule;
+}
+
+EctEnhancedCT::FramesType EctEnhancedCT::getFrames()
+{
+    return OFvisit<FramesType>(GetFramesVisitor(*this), getImagePixel());
+}
+
+OFCondition EctEnhancedCT::importFromSourceImage(DcmItem& dataset, const OFBool takeOverCharset)
+{
+    OFString FoR;
+    dataset.findAndGetOFString(DCM_FrameOfReferenceUID, FoR);
+    return IODImage::importHierarchy(dataset,
+                                     OFTrue,       // Patient
+                                     OFTrue,       // Study
+                                     !FoR.empty(), // Frame of Reference
+                                     OFFalse,      // Series
+                                     takeOverCharset);
+}
+
+OFCondition EctEnhancedCT::importFromSourceImage(const OFString& filename, const OFBool takeOverCharset)
+{
+    DcmFileFormat dcmff;
+    OFCondition result = dcmff.loadFile(filename);
+    if (result.good())
+    {
+        return importFromSourceImage(*(dcmff.getDataset()), takeOverCharset);
+    }
+    return result;
+}
+
+// ------------------- Module getters / setters -------------------------
+
+IODPatientModule& EctEnhancedCT::getIODPatientModule()
+{
+    return IODImage::getPatient();
+}
+
+IODPatientStudyModule& EctEnhancedCT::getIODPatientStudyModule()
+{
+    return IODImage::getPatientStudy();
+}
+
+IODGeneralStudyModule& EctEnhancedCT::getIODGeneralStudyModule()
+{
+    return IODImage::getStudy();
+}
+
+IODGeneralSeriesModule& EctEnhancedCT::getIODGeneralSeriesModule()
+{
+    return IODImage::getSeries();
+}
+
+IODFoRModule& EctEnhancedCT::getIODFrameOfReferenceModule()
+{
+    return IODImage::getFrameOfReference();
+}
+
+IODSynchronizationModule& EctEnhancedCT::getIODSynchronizationModule()
+{
+    return m_SynchronisationModule;
+}
+
+void EctEnhancedCT::setIODSynchronisationModuleEnabled(const OFBool enabled)
+{
+    m_SynchronisationModuleEnabled = enabled;
+}
+
+OFBool EctEnhancedCT::getIODSynchronisationModuleEnabled()
+{
+    return m_SynchronisationModuleEnabled;
+}
+
+IODGeneralEquipmentModule& EctEnhancedCT::getIODGeneralEquipmentModule()
+{
+    return IODImage::getEquipment();
+}
+
+IODEnhGeneralEquipmentModule& EctEnhancedCT::getIODEnhGeneralEquipmentModule()
+{
+    return m_EnhancedGeneralEquipmentModule;
+}
+
+IODMultiFrameFGModule& EctEnhancedCT::getIODMultiFrameFGModule()
+{
+    return m_FG;
+}
+
+IODMultiframeDimensionModule& EctEnhancedCT::getIODMultiframeDimensionModule()
+{
+    return m_DimensionModule;
+}
+
+IODAcquisitionContextModule& EctEnhancedCT::getIODAcquisitionContextModule()
+{
+    return m_AcquisitionContextModule;
+}
+
+IODSOPCommonModule& EctEnhancedCT::getIODSOPCommonModule()
+{
+    return IODImage::getSOPCommon();
+}
+
+IODCommonInstanceReferenceModule& EctEnhancedCT::getIODCommonInstanceReferenceModule()
+{
+    return m_CommonInstanceReferenceModule;
+}
+
+// --------- Getters from Image Pixel, Enhanced CT Series, as far as applicable ---------------
+
+OFCondition EctEnhancedCT::getImageType(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_ImageType, *getData(), value, pos);
+}
+
+OFCondition EctEnhancedCT::getAcquisitionNumber(Sint32& value, const unsigned long pos)
+{
+    return getData()->findAndGetSint32(DCM_AcquisitionNumber, value, pos);
+}
+
+OFCondition EctEnhancedCT::getAcquisitionNumber(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_AcquisitionNumber, *getData(), value, pos);
+}
+
+OFCondition EctEnhancedCT::getAcquisitionDateTime(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_AcquisitionDateTime, *getData(), value, pos);
+}
+
+OFCondition EctEnhancedCT::getAcquisitionDuration(Float64& value, const unsigned long pos)
+{
+    return getData()->findAndGetFloat64(DCM_AcquisitionDuration, value, pos);
+}
+
+OFCondition EctEnhancedCT::getAcquisitionDuration(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_AcquisitionDuration, *getData(), value, pos);
+}
+
+OFCondition EctEnhancedCT::getContentQualification(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_ContentQualification, *getData(), value, pos);
+}
+
+OFCondition EctEnhancedCT::getImageComments(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_ImageComments, *getData(), value, pos);
+}
+
+OFCondition EctEnhancedCT::getBurnedInAnnotation(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_BurnedInAnnotation, *getData(), value, pos);
+}
+
+OFCondition EctEnhancedCT::getRecognizableVisualFeatures(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_RecognizableVisualFeatures, *getData(), value, pos);
+}
+
+OFCondition EctEnhancedCT::getLossyImageCompression(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_LossyImageCompression, *getData(), value, pos);
+}
+
+OFCondition EctEnhancedCT::getLossyImageCompressionRatio(Float64& value, const unsigned long pos)
+{
+    return getData()->findAndGetFloat64(DCM_LossyImageCompressionRatio, value, pos);
+}
+
+OFCondition EctEnhancedCT::getLossyImageCompressionRatio(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_LossyImageCompressionRatio, *getData(), value, pos);
+}
+
+OFCondition EctEnhancedCT::getLossyImageCompressionMethod(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_LossyImageCompressionMethod, *getData(), value, pos);
+}
+
+OFCondition EctEnhancedCT::getPresentationLUTShape(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_PresentationLUTShape, *getData(), value, pos);
+}
+
+OFCondition EctEnhancedCT::getMultiEnergyCTAcquisition(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_MultienergyCTAcquisition, *getData(), value, pos);
+}
+
+OFCondition EctEnhancedCT::getPixelPresentation(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_PixelPresentation, *getData(), value, pos);
+}
+
+OFCondition EctEnhancedCT::getVolumetricProperties(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_VolumetricProperties, *getData(), value, pos);
+}
+
+OFCondition EctEnhancedCT::getVolumeBasedCalculationTechnique(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_VolumeBasedCalculationTechnique, *getData(), value, pos);
+}
+
+OFCondition EctEnhancedCT::getIsocenterPosition(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_IsocenterPosition, *getData(), value, pos);
+}
+
+OFCondition EctEnhancedCT::getIsocenterPosition(OFVector<Float64>& values)
+{
+    return DcmIODUtil::getFloat64ValuesFromItem(DCM_IsocenterPosition, *getData(), values);
+}
+
+OFCondition EctEnhancedCT::getColumns(Uint16& cols)
+{
+    return getImagePixel().getColumns(cols);
+}
+
+OFCondition EctEnhancedCT::getRows(Uint16& rows)
+{
+    return getImagePixel().getRows(rows);
+}
+
+// --------- Setters from Image Pixel, Enhanced CT Series, as far as applicable ---------------
+
+OFCondition EctEnhancedCT::setImageType(const OFString& value, const OFBool check)
+{
+    OFCondition result = (check) ? DcmCodeString::checkStringValue(value, "4") : EC_Normal;
+    if (result.good())
+        result = m_ImageType.putOFStringArray(value);
+    return result;
+}
+
+OFCondition EctEnhancedCT::setAcquisitionNumber(const OFString& value, const OFBool check)
+{
+    OFCondition result = (check) ? DcmIntegerString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_AcquisitionNumber.putOFStringArray(value);
+    return result;
+}
+
+OFCondition EctEnhancedCT::setAcquisitionDateTime(const OFString& value, const OFBool check)
+{
+    OFCondition result = (check) ? DcmDateTime::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_AcquisitionDateTime.putOFStringArray(value);
+    return result;
+}
+
+OFCondition EctEnhancedCT::setAcquisitionDuration(const Float64& value, const bool check)
+{
+    (void)check;
+    return m_AcquisitionDuration.putFloat64(value);
+}
+
+OFCondition EctEnhancedCT::setContentQualification(const EctTypes::E_ContentQualification value, const OFBool check)
+{
+    (void)check;
+    if ((value == EctTypes::E_ContentQuali_Invalid) || (value == EctTypes::E_ContentQuali_Empty))
+        return ECT_InvalidAttributeValue;
+
+    return m_ContentQualification.putOFStringArray(EctTypes::contentQualiToStr(value));
+}
+
+OFCondition EctEnhancedCT::setImageComments(const OFString& value, const OFBool check)
+{
+    OFCondition result = (check) ? DcmLongText::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_ImageComments.putOFStringArray(value);
+    return result;
+}
+
+OFCondition EctEnhancedCT::setRecognizableVisualFeatures(const EctTypes::E_RecognizableVisualFeatures value,
+                                                         const OFBool check)
+{
+    (void)check;
+    if ((value == EctTypes::E_RecoVisFeatures_Invalid) || (value == EctTypes::E_RecoVisFeatures_Empty))
+        return ECT_InvalidAttributeValue;
+
+    return m_RecognizableVisualFeatures.putOFStringArray(EctTypes::recoVisFeaturesToStr(value));
+}
+
+OFCondition EctEnhancedCT::setLossyImageCompression(const OFBool isLossy,
+                                                    const OFString& ratios,
+                                                    const OFString& methods,
+                                                    const OFBool check)
+{
+    if (!isLossy)
+    {
+        return m_LossyImageCompression.putOFStringArray("00");
+    }
+
+    OFCondition result = m_LossyImageCompression.putOFStringArray("01");
+    if (result.good())
+        result = (check) ? DcmDecimalString::checkStringValue(ratios, "1-n") : EC_Normal;
+    if (result.good())
+        result = m_LossyImageCompression.putOFStringArray(ratios);
+
+    if (result.good())
+        result = (check) ? DcmCodeString::checkStringValue(methods, "1-n") : EC_Normal;
+    if (result.good())
+        result = m_LossyImageCompressionMethod.putOFStringArray(methods);
+
+    return result;
+}
+
+OFCondition EctEnhancedCT::setISOCenterPosition(const OFVector<Float64>& values, const OFBool check)
+{
+    return DcmIODUtil::setFloat64ValuesOnElement(m_IsoCenterPosition, values, "3", check);
+}
+
+OFCondition EctEnhancedCT::setISOCenterPosition(const OFString& value, const OFBool check)
+{
+    OFCondition result = (check) ? DcmDecimalString::checkStringValue(value, "3") : EC_Normal;
+    if (result.good())
+        result = m_IsoCenterPosition.putOFStringArray(value);
+    return result;
+}
+
+OFCondition EctEnhancedCT::setMultiEnergyCTAcquisition(const OFString& value, const OFBool check)
+{
+    OFCondition result = (check) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_MultiEnergyCTAcquisition.putOFStringArray(value);
+    return result;
+}
+
+OFCondition EctEnhancedCT::setPixelPresentation(const EctTypes::E_PixelPresentation value, const OFBool check)
+{
+    (void)check;
+    if ((value == EctTypes::E_PixelPres_Empty) || (value == EctTypes::E_PixelPres_Invalid))
+        return ECT_InvalidAttributeValue;
+
+    return m_PixelPresentation.putOFStringArray(EctTypes::pixelPresToStr(value));
+}
+
+OFCondition EctEnhancedCT::setVolumetricProperties(const EctTypes::E_VolumetricProperties value, const OFBool check)
+{
+    (void)check;
+    if ((value == EctTypes::E_VolProps_Empty) || (value == EctTypes::E_VolProps_Invalid))
+        return ECT_InvalidAttributeValue;
+
+    return m_VolumetricProperties.putOFStringArray(EctTypes::volPropsToStr(value));
+}
+
+OFCondition EctEnhancedCT::setVolumeBasedCalculationTechnique(const OFString& value, const OFBool check)
+{
+    OFCondition result = (check) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_VolumeBasedCalculationTechnique.putOFStringArray(value);
+    return result;
+}
+
+// -------------------- Protected Helpers --------------------------
+
+OFCondition EctEnhancedCT::read(DcmItem& dataset)
+{
+    OFCondition result = OFvisit<OFCondition>(ReadVisitor(dataset, *this), getImagePixel());
+    return result;
+}
+
+OFCondition EctEnhancedCT::write(DcmItem& dataset)
+{
+    if (!check())
+    {
+        return IOD_EC_InvalidObject;
+    }
+
+    OFCondition result = OFvisit<OFCondition>(WriteVisitor(dataset, *this), getImagePixel());
+    if (result.good())
+        result = writeGeneric(dataset);
+    return result;
+}
+
+OFCondition EctEnhancedCT::writeConcatenation(ConcatenationCreator& cc)
+{
+    if (!check())
+    {
+        return IOD_EC_InvalidObject;
+    }
+
+    DcmItem* item = new DcmItem();
+    if (!item)
+        return EC_MemoryExhausted;
+
+    Uint8* pixData       = NULL;
+    size_t pixDataLength = 0;
+
+    OFCondition result
+        = OFvisit<OFCondition>(WriteVisitorConcatenation(*this, pixData, pixDataLength), getImagePixel());
+
+    if (result.good())
+        result = writeGeneric(*item);
+    if (result.good())
+    {
+        result = cc.setCfgInput(item, pixData, pixDataLength, OFTrue /* cc should take ownership */);
+    }
+    return result;
+}
+
+OFCondition EctEnhancedCT::writeGeneric(DcmItem& dataset)
+{
+    OFCondition result;
+    if (m_SynchronisationModuleEnabled)
+        result = m_SynchronisationModule.write(dataset);
+    if (result.good())
+        result = m_FG.setNumberOfFrames(
+            DcmIODUtil::limitMaxFrames(m_Frames.size(), "Maximum number of frames exceeded, will write 2147483647"));
+    if (result.good())
+        result = m_FG.write(dataset);
+    if (result.good())
+        result = m_FGInterface.write(dataset);
+    if (result.good())
+        result = m_DimensionModule.write(dataset);
+    if (result.good())
+        result = m_AcquisitionContextModule.write(dataset);
+    if (result.good())
+        result = m_CommonInstanceReferenceModule.write(dataset);
+    if (result.good())
+        result = getIODGeneralSeriesModule().setModality("CT");
+    if (result.good())
+        result = IODImage::write(dataset);
+    // Write after General Equipment Module from IODImage
+    if (result.good())
+        result = m_EnhancedGeneralEquipmentModule.write(dataset);
+
+    if (result.good())
+        result = DcmIODUtil::copyElementToDataset(
+            result, dataset, m_ImageType, "4" /* vm */, "1" /*requirement type*/, "EnhancedCTImageModule");
+    if (result.good())
+        result = DcmIODUtil::copyElementToDataset(
+            result, dataset, m_MultiEnergyCTAcquisition, "1", "3", "EnhancedCTImageModule");
+    if (result.good())
+        result
+            = DcmIODUtil::copyElementToDataset(result, dataset, m_PixelPresentation, "1", "1", "EnhancedCTImageModule");
+    if (result.good())
+        result = DcmIODUtil::copyElementToDataset(
+            result, dataset, m_VolumetricProperties, "1", "1", "EnhancedCTImageModule");
+    if (result.good())
+        result = DcmIODUtil::copyElementToDataset(
+            result, dataset, m_VolumeBasedCalculationTechnique, "1", "1", "EnhancedCTImageModule");
+    if (result.good())
+        result
+            = DcmIODUtil::copyElementToDataset(result, dataset, m_AcquisitionNumber, "1", "3", "EnhancedCTImageModule");
+    if (result.good())
+        result = DcmIODUtil::copyElementToDataset(
+            result, dataset, m_AcquisitionDateTime, "1", "1C", "EnhancedCTImageModule");
+    if (result.good())
+        result = DcmIODUtil::copyElementToDataset(
+            result, dataset, m_AcquisitionDuration, "1", "1C", "EnhancedCTImageModule");
+    if (result.good())
+        result = DcmIODUtil::copyElementToDataset(
+            result, dataset, m_ContentQualification, "1", "1C", "EnhancedCTImageModule");
+    if (result.good())
+        result = DcmIODUtil::copyElementToDataset(result, dataset, m_ImageComments, "1", "3", "EnhancedCTImageModule");
+    if (result.good())
+        result = DcmIODUtil::copyElementToDataset(
+            result, dataset, m_BurnedInAnnotation, "1", "1C", "EnhancedCTImageModule");
+    if (result.good())
+        result = DcmIODUtil::copyElementToDataset(
+            result, dataset, m_RecognizableVisualFeatures, "1", "3", "EnhancedCTImageModule");
+    if (result.good())
+        result = DcmIODUtil::copyElementToDataset(
+            result, dataset, m_LossyImageCompression, "1", "1", "EnhancedCTImageModule");
+    if (result.good())
+        result = DcmIODUtil::copyElementToDataset(
+            result, dataset, m_LossyImageCompressionMethod, "1-n", "1C", "EnhancedCTImageModule");
+
+    if (result.good())
+        result = DcmIODUtil::copyElementToDataset(
+            result, dataset, m_LossyImageCompressionRatio, "1-n", "1C", "EnhancedCTImageModule");
+
+    m_PresentationLUTShape.putOFStringArray("IDENTITY");
+    if (result.good())
+        result = DcmIODUtil::copyElementToDataset(
+            result, dataset, m_PresentationLUTShape, "1", "1", "EnhancedCTImageModule");
+    if (result.good())
+        result
+            = DcmIODUtil::copyElementToDataset(result, dataset, m_IsoCenterPosition, "3", "3", "EnhancedCTImageModule");
+    return result;
+}
+
+OFCondition EctEnhancedCT::readGeneric(DcmItem& dataset)
+{
+    OFString sopClass;
+    if (DcmIODUtil::checkSOPClass(&dataset, UID_EnhancedCTImageStorage, sopClass).bad())
+    {
+        DCMECT_ERROR("Given file does not seem to be a Enhanced CT storage object since SOP class is: " << sopClass);
+        return IOD_EC_WrongSOPClass;
+    }
+
+    IODImage::read(dataset);
+    m_SynchronisationModule.read(dataset);
+    m_EnhancedGeneralEquipmentModule.read(dataset);
+    m_FG.read(dataset);
+    m_DimensionModule.read(dataset);
+    m_AcquisitionContextModule.read(dataset);
+    m_CommonInstanceReferenceModule.read(dataset);
+    m_FGInterface.read(dataset);
+
+    // Enhanced CT Image Module
+    DcmIODUtil::getAndCheckElementFromDataset(dataset, m_ImageType, "4", "1C", "EnhancedCTImageModule");
+    DcmIODUtil::getAndCheckElementFromDataset(dataset, m_MultiEnergyCTAcquisition, "1", "3", "EnhancedCTImageModule");
+    DcmIODUtil::getAndCheckElementFromDataset(dataset, m_PixelPresentation, "1", "1", "EnhancedCTImageModule");
+    DcmIODUtil::getAndCheckElementFromDataset(dataset, m_VolumetricProperties, "1", "1", "EnhancedCTImageModule");
+    DcmIODUtil::getAndCheckElementFromDataset(
+        dataset, m_VolumeBasedCalculationTechnique, "1", "1", "EnhancedCTImageModule");
+    DcmIODUtil::getAndCheckElementFromDataset(dataset, m_AcquisitionNumber, "1", "3", "EnhancedCTImageModule");
+    DcmIODUtil::getAndCheckElementFromDataset(dataset, m_AcquisitionDateTime, "1", "1C", "EnhancedCTImageModule");
+    DcmIODUtil::getAndCheckElementFromDataset(dataset, m_AcquisitionDuration, "1", "1C", "EnhancedCTImageModule");
+    DcmIODUtil::getAndCheckElementFromDataset(dataset, m_ContentQualification, "1", "1C", "EnhancedCTImageModule");
+    DcmIODUtil::getAndCheckElementFromDataset(dataset, m_BurnedInAnnotation, "1", "1C", "EnhancedCTImageModule");
+    DcmIODUtil::getAndCheckElementFromDataset(dataset, m_RecognizableVisualFeatures, "1", "3", "EnhancedCTImageModule");
+    DcmIODUtil::getAndCheckElementFromDataset(dataset, m_LossyImageCompression, "1", "1", "EnhancedCTImageModule");
+    DcmIODUtil::getAndCheckElementFromDataset(
+        dataset, m_LossyImageCompressionMethod, "1-n", "1C", "EnhancedCTImageModule");
+    DcmIODUtil::getAndCheckElementFromDataset(
+        dataset, m_LossyImageCompressionRatio, "1-n", "1C", "EnhancedCTImageModule");
+    DcmIODUtil::getAndCheckElementFromDataset(dataset, m_PresentationLUTShape, "1", "1", "EnhancedCTImageModule");
+    DcmIODUtil::getAndCheckElementFromDataset(dataset, m_IsoCenterPosition, "3", "3", "EnhancedCTImageModule");
+    return EC_Normal;
+}
+
+OFCondition EctEnhancedCT::decompress(DcmDataset& dset)
+{
+    DcmXfer xfer = dset.getOriginalXfer();
+    OFCondition result;
+    // If the original transfer is encapsulated and we do not already have an uncompressed version, decompress or reject
+    // the file
+    if (xfer.isEncapsulated())
+    {
+        DCMECT_DEBUG("Enhanced CT object is compressed, converting to uncompressed transfer syntax first");
+        result = DcmIODUtil::decompress(dset);
+    }
+    return result;
+}
+
+// Instantiate Frames template with both possible pixel data types
+template class EctEnhancedCT::Frames<Uint16>;
+template class EctEnhancedCT::Frames<Sint16>;
diff --git a/dcmect/libsrc/types.cc b/dcmect/libsrc/types.cc
new file mode 100644 (file)
index 0000000..2a2741a
--- /dev/null
@@ -0,0 +1,248 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing common Enhanced CT-specific types
+ *
+ */
+
+#include "dcmtk/dcmect/types.h"
+#include "dcmtk/config/osconfig.h"
+#include "dcmtk/dcmdata/dcerror.h"
+
+OFLogger DCM_dcmectLogger = OFLog::getLogger("dcmtk.dcmect");
+
+/*---------------------------------*
+ *  constant definitions
+ *---------------------------------*/
+
+// conditions
+// makeOFConditionConst(ECT_EC_....,      OFM_dcmect, 1, OF_error, "...");
+
+const OFString EctTypes::DT_ImageType3_Angio         = "ANGIO";
+const OFString EctTypes::DT_ImageType3_Cardiac       = "CARDICAC";
+const OFString EctTypes::DT_ImageType3_CardiacGated  = "CARDIAC_GATED";
+const OFString EctTypes::DT_ImageType3_CardRespGated = "CARDRESP_GATED";
+const OFString EctTypes::DT_ImageType3_Dynamic       = "DYNAMIC";
+const OFString EctTypes::DT_ImageType3_Fluoroscopy   = "FLOUROSCOPY";
+const OFString EctTypes::DT_ImageType3_Localizer     = "LOCALIZER";
+const OFString EctTypes::DT_ImageType3_Motion        = "MOTION";
+const OFString EctTypes::DT_ImageType3_Perfusion     = "PERFUSION";
+const OFString EctTypes::DT_ImageType3_PreContrast   = "PRE_CONTRAST";
+const OFString EctTypes::DT_ImageType3_PostContrast  = "POST_CONTRAST";
+const OFString EctTypes::DT_ImageType3_RespGated     = "RESP_GATED";
+const OFString EctTypes::DT_ImageType3_Rest          = "REST";
+const OFString EctTypes::DT_ImageType3_Static        = "STATIC";
+const OFString EctTypes::DT_ImageType3_Stress        = "STRESS";
+const OFString EctTypes::DT_ImageType3_Volume        = "VOLUME";
+const OFString EctTypes::DT_ImageType3_NonParallel   = "NON_PARALLEL";
+const OFString EctTypes::DT_ImageType3_WholeBody     = "WHOLE_BODY";
+
+const OFString EctTypes::DT_ImageType4_Addition       = "ADDITION";
+const OFString EctTypes::DT_ImageType4_Division       = "DIVISION";
+const OFString EctTypes::DT_ImageType4_Masked         = "MASKED";
+const OFString EctTypes::DT_ImageType4_Maximum        = "MAXIMUM";
+const OFString EctTypes::DT_ImageType4_Mean           = "MEAN";
+const OFString EctTypes::DT_ImageType4_Minimum        = "MINIMUM";
+const OFString EctTypes::DT_ImageType4_Multiplication = "MULTIPLICATION";
+const OFString EctTypes::DT_ImageType4_Resampled      = "RESAMPLED";
+const OFString EctTypes::DT_ImageType4_Std_Deviation  = "STD_DEVIATION";
+const OFString EctTypes::DT_ImageType4_Subtraction    = "SUBTRACTION";
+const OFString EctTypes::DT_ImageType4_None           = "NONE";
+const OFString EctTypes::DT_ImageType4_Quantity       = "QUANTITY";
+const OFString EctTypes::DT_ImageType4_Mixed          = "MIXED";
+
+const OFString EctTypes::DT_VolBasedCalcTechnique_MaxIp         = "MAX_IP";
+const OFString EctTypes::DT_VolBasedCalcTechnique_MinIp         = "MIN_IP";
+const OFString EctTypes::DT_VolBasedCalcTechnique_VolumeRender  = "VOLUME_RENDER";
+const OFString EctTypes::DT_VolBasedCalcTechnique_SurfaceRender = "SURFACE_RENDER";
+const OFString EctTypes::DT_VolBasedCalcTechnique_Mpr           = "MPR";
+const OFString EctTypes::DT_VolBasedCalcTechnique_CurvedMpr     = "CURVED_MPR";
+const OFString EctTypes::DT_VolBasedCalcTechnique_None          = "NONE";
+const OFString EctTypes::DT_VolBasedCalcTechnique_Mixed         = "MIXED";
+
+// conditions
+makeOFConditionConst(ECT_InvalidDimensions, OFM_dcmect, 1, OF_error, "Invalid Dimensions");
+makeOFConditionConst(ECT_InvalidAttributeValue, OFM_dcmect, 2, OF_error, "Invalid Attribute Value");
+makeOFConditionConst(
+    ECT_InvalidPixelInfo, OFM_dcmect, 3, OF_error, "Invalid information in pixel data or related attributes");
+makeOFConditionConst(ECT_InvalidPixelData, OFM_dcmect, 4, OF_error, "Invalid pixel data");
+makeOFConditionConst(ECT_NoPixelData, OFM_dcmect, 5, OF_error, "No pixel data found");
+makeOFConditionConst(ECT_InvalidSOPClass, OFM_dcmect, 6, OF_error, "SOP Class not supported");
+
+OFString EctTypes::imageType1ToStr(const E_ImageType1 value)
+{
+    switch (value)
+    {
+        case E_ImageType1_Empty:
+            return "";
+            break;
+        case E_ImageType1_Invalid:
+            return "";
+            break;
+        case E_ImageType1_Original:
+            return "ORIGINAL";
+            break;
+        case E_ImageType1_Derived:
+            return "DERIVED";
+            break;
+        case E_ImageType1_Mixed:
+            return "MIXED";
+            break;
+        default:
+            DCMECT_ERROR("Internal error, invalid value for E_ImageType1: " << value);
+            return "";
+    }
+}
+
+OFString EctTypes::imageType2ToStr(const E_ImageType2 value)
+{
+    switch (value)
+    {
+        case E_ImageType2_Empty:
+            return "";
+            break;
+        case E_ImageType2_Invalid:
+            return "";
+            break;
+        case E_ImageType2_Primary:
+            return "PRIMARY";
+            break;
+        default:
+            DCMECT_ERROR("Internal error, invalid value for E_ImageType2: " << value);
+            return "";
+    }
+}
+
+OFString EctTypes::contentQualiToStr(const E_ContentQualification value)
+{
+    switch (value)
+    {
+        case E_ContentQuali_Empty:
+            return "";
+            break;
+        case E_ContentQuali_Invalid:
+            return "";
+            break;
+        case E_ContQuali_Product:
+            return "PRODUCT";
+            break;
+        case E_ContQuali_Research:
+            return "RESEARCH";
+            break;
+        case E_ContQuali_Service:
+            return "SERVICE";
+            break;
+        default:
+            DCMECT_ERROR("Internal error, invalid value for E_ContentQualification: " << value);
+            return "";
+    }
+}
+
+OFString EctTypes::burnedAnnoToStr(const E_BurnedInAnnotation value)
+{
+    switch (value)
+    {
+        case E_BurnedInAnno_Empty:
+            return "";
+            break;
+        case E_BurnedInAnno_Invalid:
+            return "";
+            break;
+        case E_BurnedInAnno_No:
+            return "NO";
+            break;
+        default:
+            DCMECT_ERROR("Internal error, invalid value for E_BurnedInAnnotation: " << value);
+            return "";
+    }
+}
+
+OFString EctTypes::pixelPresToStr(const E_PixelPresentation value)
+{
+    switch (value)
+    {
+        case E_PixelPres_Empty:
+            return "";
+            break;
+        case E_PixelPres_Invalid:
+            return "";
+            break;
+        case E_PixelPres_Color:
+            return "COLOR";
+            break;
+        case E_PixelPres_Mixed:
+            return "MIXED";
+            break;
+        case E_PixelPres_Monochrome:
+            return "MONOCHROME";
+        case E_PixelPres_TrueColor:
+            return "TRUE_COLOR";
+        default:
+            DCMECT_ERROR("Internal error, invalid value for E_PixelPresentation: " << value);
+            return "";
+    }
+}
+
+OFString EctTypes::volPropsToStr(const E_VolumetricProperties value)
+{
+    switch (value)
+    {
+        case E_VolProps_Empty:
+            return "";
+            break;
+        case E_VolProps_Invalid:
+            return "";
+            break;
+        case E_VolProps_Distorted:
+            return "DISTORTED";
+            break;
+        case E_VolProps_Mixed:
+            return "MIXED";
+            break;
+        case E_VolProps_Sampled:
+            return "SAMPLED";
+            break;
+        case E_VolProps_Volume:
+            return "VOLUME";
+            break;
+        default:
+            DCMECT_ERROR("Internal error, invalid value for E_VolumetricProperties: " << value);
+            return "";
+    }
+}
+
+OFString EctTypes::recoVisFeaturesToStr(const E_RecognizableVisualFeatures value)
+{
+    switch (value)
+    {
+        case E_RecoVisFeatures_Empty:
+            return "";
+            break;
+        case E_RecoVisFeatures_Invalid:
+            return "";
+            break;
+        case E_RecoVisFeatures_No:
+            return "NO";
+            break;
+        case E_RecoVisFeatures_Yes:
+            return "YES";
+            break;
+        default:
+            DCMECT_ERROR("Internal error, invalid value for E_RecognizableVisualFeatures: " << value);
+            return "";
+    }
+}
diff --git a/dcmect/tests/CMakeLists.txt b/dcmect/tests/CMakeLists.txt
new file mode 100644 (file)
index 0000000..01e732d
--- /dev/null
@@ -0,0 +1,11 @@
+# declare executables
+DCMTK_ADD_EXECUTABLE(dcmect_tests
+                     tests
+                     t_huge_concat
+                     t_roundtrip)
+
+# make sure executables are linked to the corresponding libraries
+DCMTK_TARGET_LINK_MODULES(dcmect_tests dcmect dcmfg dcmdata oflog ofstd)
+
+# This macro parses tests.cc and registers all tests
+DCMTK_ADD_TESTS(dcmect)
diff --git a/dcmect/tests/Makefile.dep b/dcmect/tests/Makefile.dep
new file mode 100644 (file)
index 0000000..ba8cdd4
--- /dev/null
@@ -0,0 +1,437 @@
+t_huge_concat.o: t_huge_concat.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstrutl.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/oftempf.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../include/dcmtk/dcmect/enhanced_ct.h ../include/dcmtk/dcmect/def.h \
+ ../include/dcmtk/dcmect/types.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fginterface.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fg.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgbase.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodimage.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodcommn.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modpatient.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modpatientstudy.h \
+ ../../ofstd/include/dcmtk/ofstd/ofoption.h \
+ ../../ofstd/include/dcmtk/ofstd/ofalign.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modsopcommon.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralimage.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixelvariant.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixelbase.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvriant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/variant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/helpers.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdiag.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/push.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/cnvrsn.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/vsprfw.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/pop.def \
+ ../../dcmiod/include/dcmtk/dcmiod/modacquisitioncontext.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modenhequipment.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixel.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modmultiframedimension.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modmultiframefg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modsynchronisation.h \
+ ../../dcmfg/include/dcmtk/dcmfg/concatenationcreator.h \
+ ../../dcmfg/include/dcmtk/dcmfg/concatenationloader.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../ofstd/include/dcmtk/ofstd/oftuple.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/mmtag.def \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefrd.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuple.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctacquisitiondetails.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctacquisitiontype.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctadditionalxraysource.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctexposure.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctgeometry.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctimageframetype.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctposition.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctreconstruction.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgcttabledynamics.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctxraydetails.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgfracon.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgframeanatomy.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgframevoilut.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgirradiationeventid.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgpixeltransform.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgpixmsr.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgplanor.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgplanpo.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgrealworldvaluemapping.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodcontentitemmacro.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgtemporalposition.h
+t_roundtrip.o: t_roundtrip.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstrutl.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/oftempf.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../include/dcmtk/dcmect/enhanced_ct.h ../include/dcmtk/dcmect/def.h \
+ ../include/dcmtk/dcmect/types.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fginterface.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fg.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgbase.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodimage.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodcommn.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modpatient.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modpatientstudy.h \
+ ../../ofstd/include/dcmtk/ofstd/ofoption.h \
+ ../../ofstd/include/dcmtk/ofstd/ofalign.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modsopcommon.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralimage.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixelvariant.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixelbase.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvriant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/variant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/helpers.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdiag.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/push.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/cnvrsn.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/vsprfw.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/pop.def \
+ ../../dcmiod/include/dcmtk/dcmiod/modacquisitioncontext.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modenhequipment.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixel.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modmultiframedimension.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modmultiframefg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modsynchronisation.h \
+ ../../dcmfg/include/dcmtk/dcmfg/concatenationcreator.h \
+ ../../dcmfg/include/dcmtk/dcmfg/concatenationloader.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../ofstd/include/dcmtk/ofstd/oftuple.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/mmtag.def \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefrd.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuple.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctacquisitiondetails.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctacquisitiontype.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctadditionalxraysource.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctexposure.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctgeometry.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctimageframetype.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctposition.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctreconstruction.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgcttabledynamics.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgctxraydetails.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgfracon.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgframeanatomy.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgframevoilut.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgirradiationeventid.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgpixeltransform.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgpixmsr.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgplanor.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgplanpo.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgrealworldvaluemapping.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodcontentitemmacro.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgtemporalposition.h
+tests.o: tests.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h
diff --git a/dcmect/tests/Makefile.in b/dcmect/tests/Makefile.in
new file mode 100644 (file)
index 0000000..78b6ae5
--- /dev/null
@@ -0,0 +1,59 @@
+#
+#      Makefile for dcmect/tests
+#
+
+@SET_MAKE@
+
+SHELL = /bin/sh
+VPATH = @srcdir@:@top_srcdir@/include:@top_srcdir@/@configdir@/include
+srcdir = @srcdir@
+top_srcdir = @top_srcdir@
+configdir = @top_srcdir@/@configdir@
+
+include $(configdir)/@common_makefile@
+
+ofstddir = $(top_srcdir)/../ofstd
+oflogdir = $(top_srcdir)/../oflog
+dcmdatadir = $(top_srcdir)/../dcmdata
+dcmioddir = $(top_srcdir)/../dcmiod
+dcmfgdir = $(top_srcdir)/../dcmfg
+
+LIBDIRS = -L$(top_srcdir)/libsrc -L$(ofstddir)/libsrc -L$(oflogdir)/libsrc \
+       -L$(dcmdatadir)/libsrc -L$(dcmioddir)/libsrc -L$(dcmfgdir)/libsrc
+LOCALLIBS = -ldcmect -ldcmfg -ldcmiod -ldcmdata -loflog -lofstd $(ZLIBLIBS) \
+       $(CHARCONVLIBS) $(MATHLIBS)
+LOCALINCLUDES = -I$(top_srcdir)/include -I$(ofstddir)/include -I$(oflogdir)/include \
+       -I$(dcmdatadir)/include -I$(dcmioddir)/include -I$(dcmfgdir)/include
+
+test_objs = tests.o t_huge_concat.o t_roundtrip.o
+objs = $(test_objs)
+progs = tests
+
+
+all: $(progs)
+
+tests: $(test_objs)
+       $(CXX) $(CXXFLAGS) $(LIBDIRS) $(LDFLAGS) $(LOCALINCLUDES) -o $@ $(test_objs) $(LOCALLIBS) $(LIBS)
+
+
+check: tests
+       DCMDICTPATH=../../dcmdata/data/dicom.dic ./tests
+
+check-exhaustive: tests
+       DCMDICTPATH=../../dcmdata/data/dicom.dic ./tests -x
+
+
+install: all
+
+
+clean:
+       rm -f $(objs) $(progs) $(LOCALTRASH) $(TRASH)
+
+distclean:
+       rm -f $(objs) $(progs) $(LOCALTRASH) $(DISTTRASH)
+
+
+dependencies:
+       $(CXX) -MM $(defines) $(includes) $(CPPFLAGS) $(CXXFLAGS) *.cc  > $(DEP)
+
+include $(DEP)
diff --git a/dcmect/tests/t_huge_concat.cc b/dcmect/tests/t_huge_concat.cc
new file mode 100644 (file)
index 0000000..c96b2fa
--- /dev/null
@@ -0,0 +1,973 @@
+/*
+ *
+ *  Copyright (C) 2019-2020, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmect
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Tests for creating huge (> 4 GB) Enhanced CT objects
+ *
+ */
+
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+
+#include "dcmtk/ofstd/ofmem.h"
+#include "dcmtk/ofstd/ofstrutl.h"
+#include "dcmtk/ofstd/oftempf.h"
+#include "dcmtk/ofstd/oftest.h"
+
+#include "dcmtk/dcmdata/dctypes.h"
+
+#include "dcmtk/dcmect/enhanced_ct.h"
+
+#include "dcmtk/dcmfg/concatenationcreator.h"
+#include "dcmtk/dcmfg/concatenationloader.h"
+#include "dcmtk/dcmfg/fgctacquisitiondetails.h"
+#include "dcmtk/dcmfg/fgctacquisitiontype.h"
+#include "dcmtk/dcmfg/fgctadditionalxraysource.h"
+#include "dcmtk/dcmfg/fgctexposure.h"
+#include "dcmtk/dcmfg/fgctgeometry.h"
+#include "dcmtk/dcmfg/fgctimageframetype.h"
+#include "dcmtk/dcmfg/fgctposition.h"
+#include "dcmtk/dcmfg/fgctreconstruction.h"
+#include "dcmtk/dcmfg/fgcttabledynamics.h"
+#include "dcmtk/dcmfg/fgctxraydetails.h"
+#include "dcmtk/dcmfg/fgfracon.h"
+#include "dcmtk/dcmfg/fgframeanatomy.h"
+#include "dcmtk/dcmfg/fgframevoilut.h"
+#include "dcmtk/dcmfg/fgirradiationeventid.h"
+#include "dcmtk/dcmfg/fgpixeltransform.h"
+#include "dcmtk/dcmfg/fgpixmsr.h"
+#include "dcmtk/dcmfg/fgplanor.h"
+#include "dcmtk/dcmfg/fgplanpo.h"
+#include "dcmtk/dcmfg/fgrealworldvaluemapping.h"
+#include "dcmtk/dcmfg/fgtemporalposition.h"
+
+static OFLogger tRoundLogger = OFLog::getLogger("dcmtk.test.t_huge_concat");
+
+// Number of Rows of image, might be changed for testing purposes
+static const Uint16 NUM_ROWS = 4000;
+// Number of Columns of image, might be changed for testing purposes
+static const Uint16 NUM_COLS = 4000;
+// Number of Frames of source image, might be changed for testing purposes
+static const Uint16 NUM_FRAMES = 200;
+// Number of Frames of in concatenation images, should not be changed since the
+// dumped checked against will assume Number of Frames = 1
+static const size_t NUM_FRAMES_CONCAT    = 1;
+static const size_t NUM_PIXELS_PER_FRAME = NUM_COLS * NUM_ROWS;
+
+static const OFString CONCAT_SOP_INST_UID = "1.2.276.0.7230010.3.1.4.8323329.21580.1571390622.913190";
+static const OFString CONCATATENATION_UID = "1.2.276.0.7230010.3.1.4.8323329.23689.1571391649.103636";
+
+static OFString EXPECTED_DUMP;
+
+static void prepareExpectedDump();
+static EctEnhancedCT* create();
+static void configureIOD(EctEnhancedCT* ct);
+static void setGenericValues(EctEnhancedCT* ct);
+static void addSharedFGs(EctEnhancedCT* ct);
+static void addFrames(EctEnhancedCT* ct);
+static void addDimensions(EctEnhancedCT* ct);
+static void checkCreatedObject(const OFString& ds_dump);
+static void writeAndCheckConcatenation(EctEnhancedCT* ct, OFList<OFFilename>& concats);
+static void checkConcatenationInstance(size_t numInstance, EctEnhancedCT* srcInstance, DcmDataset* concatInstance);
+static void loadAndCheckConcatenation(const OFList<OFFilename>& concats);
+
+OFTEST_FLAGS(dcmect_huge_concat, EF_Slow)
+{
+    /* make sure data dictionary is loaded */
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK(dcmDataDict.isDictionaryLoaded());
+        return;
+    }
+
+    // Creation
+    EctEnhancedCT* ct = create();
+    configureIOD(ct);
+    setGenericValues(ct);
+    addSharedFGs(ct);
+    addFrames(ct);
+    addDimensions(ct);
+
+    prepareExpectedDump();
+
+    OFList<OFFilename> concats;
+    if (ct)
+    {
+        writeAndCheckConcatenation(ct, concats);
+        delete ct;
+    }
+    OFCHECK(!concats.empty());
+    if (!concats.empty())
+    {
+        loadAndCheckConcatenation(concats);
+    }
+    OFListIterator(OFFilename) it = concats.begin();
+    while (it != concats.end())
+    {
+        OFStandard::deleteFile(*it);
+        it++;
+    }
+}
+
+static EctEnhancedCT* create()
+{
+    IODEnhGeneralEquipmentModule::EquipmentInfo eq("Open Connections", "OC CT", "4711", "0.1");
+    EctEnhancedCT* ct = NULL;
+    OFCondition result;
+    result = EctEnhancedCT::create(ct,
+                                   NUM_ROWS,
+                                   NUM_COLS,
+                                   OFFalse,
+                                   EctTypes::E_ImageType1_Original,
+                                   EctTypes::DT_ImageType3_Volume,
+                                   EctTypes::DT_ImageType4_Maximum,
+                                   "1" /* instance number */,
+                                   EctTypes::E_ContQuali_Research,
+                                   EctTypes::E_PixelPres_Monochrome,
+                                   EctTypes::E_VolProps_Volume,
+                                   EctTypes::DT_VolBasedCalcTechnique_VolumeRender,
+                                   eq,
+                                   "20190801120000" /* acquisition date */,
+                                   2.0 /* acquisition duration */);
+
+    OFCHECK(result.good());
+    OFCHECK(ct != OFnullptr);
+    return ct;
+}
+
+static void configureIOD(EctEnhancedCT* ct)
+{
+    if (!ct)
+        return;
+}
+
+static void setGenericValues(EctEnhancedCT* ct)
+{
+    if (!ct)
+        return;
+    OFCHECK(ct->getPatient().setPatientName("Bond^James").good());
+    OFCHECK(ct->getPatient().setPatientID("007").good());
+    OFCHECK(ct->getPatient().setPatientBirthDate("19771007").good());
+    OFCHECK(ct->getStudy().setStudyDate("20190801").good());
+    OFCHECK(ct->getStudy().setStudyTime("120000").good());
+    OFCHECK(ct->getStudy().setStudyID("1").good());
+    OFCHECK(ct->getPatientStudy().setPatientAge("040Y").good());
+    OFCHECK(ct->getSeries().setSeriesDescription("Test Description").good());
+    OFCHECK(ct->getSeries().setSeriesNumber("1").good());
+    OFCHECK(ct->getSeries().setPatientPosition("HFS").good());
+
+    // Those values are usually computed automatically. UIDS are generated and date/times are set to current values.
+    // But in order to compare the "old" dump with the freshly created image attributes, we set some values manually,
+    // so that they are not overwritten with new, automatically created values later.
+    OFCHECK(ct->getStudy().setStudyInstanceUID("1.2.276.0.7230010.3.1.2.8323329.14863.1565940357.864811").good());
+    OFCHECK(ct->getFrameOfReference().setFrameOfReferenceUID("2.25.30853397773651184949181049330553108086").good());
+    OFCHECK(ct->getSeries().setSeriesInstanceUID("1.2.276.0.7230010.3.1.3.8323329.14863.1565940357.864812").good());
+    OFCHECK(ct->getSOPCommon().setSOPInstanceUID("1.2.276.0.7230010.3.1.4.8323329.14863.1565940357.864813").good());
+
+    OFCHECK(ct->getIODMultiFrameFGModule().setContentTime("092557").good());
+    OFCHECK(ct->getIODMultiFrameFGModule().setContentDate("20190816").good());
+}
+
+static void addSharedFGs(EctEnhancedCT* ct)
+{
+    if (!ct)
+        return;
+
+    FGPixelMeasures meas;
+    OFCHECK(meas.setPixelSpacing("0.1\\0.1").good());
+    OFCHECK(meas.setSliceThickness("1.0").good());
+    OFCHECK(meas.setSpacingBetweenSlices("0.05").good());
+
+    FGPlanePosPatient planpo;
+    OFCHECK(planpo.setImagePositionPatient("0.0", "0.0", "0.0").good());
+
+    FGPlaneOrientationPatient planor;
+    OFCHECK(planor.setImageOrientationPatient("1.0", "0.0", "0.0", "0.0", "1.0", "0.0").good());
+
+    FGFrameAnatomy ana;
+    OFCHECK(ana.setLaterality(FGFrameAnatomy::LATERALITY_BOTH).good());
+    OFCHECK(ana.getAnatomy().getAnatomicRegion().set("12738006", "SCT", "Brain").good());
+
+    FGFrameVOILUT voi;
+    OFCHECK(voi.setCenterWidthExplanation(1000, 2000, FGFrameVOILUT::DT_CT_WindowCenterWidthExplanation_Brain).good());
+
+    FGIrradiationEventIdentification irr;
+    OFCHECK(irr.setIrradiationEventUID("2.25.30853892236613436472911970638347155062").good());
+
+    FGCTImageFrameType itype;
+    OFCHECK(itype.setFrameType("ORIGINAL\\PRIMARY\\VOLUME\\MAXIMUM").good());
+    OFCHECK(itype.setPixelPresentation(FGCTImageFrameType::E_PixelPres_Monochrome).good());
+    OFCHECK(itype.setVolumetricProperties(FGCTImageFrameType::E_VolProp_Volume).good());
+    OFCHECK(itype.setVolumeBasedCalculationTechnique(FGCTImageFrameType::DT_VolBasedCalcTechnique_VolumeRender).good());
+
+    FGCTAcquisitionType atype;
+    OFCHECK(atype.setAcquisitionType(FGCTAcquisitionType::DT_AcquisitionType_ConstantAngle).good());
+    OFCHECK(atype.setTubeAngle(0.1).good());
+    OFCHECK(atype.setConstantVolumeFlag(FGCTAcquisitionType::E_ConstVol_Yes).good());
+    OFCHECK(atype.setFluoroscopyFlag(FGCTAcquisitionType::E_Fluoroscopy_No).good());
+
+    FGCTAcquisitionDetails adetails;
+    FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem* item = new FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem();
+    OFCHECK(item->setRotationDirection(FGCTAcquisitionDetails::E_RotationDirection_CW).good());
+    OFCHECK(item->setRevolutionTime(5).good());
+    OFCHECK(item->setSingleCollimationWidth(1).good());
+    OFCHECK(item->setTotalCollimationWidth(10).good());
+    OFCHECK(item->setTableHeight(50).good());
+    OFCHECK(item->setGantryDetectorTilt(5).good());
+    OFCHECK(item->setDataCollectionDiameter(20).good());
+    adetails.getCTAcquisitionDetailsItems().push_back(item);
+
+    FGCTTableDynamics dyn;
+    FGCTTableDynamics::FGCTTableDynamicsItem* dyn_item = new FGCTTableDynamics::FGCTTableDynamicsItem;
+    OFCHECK(dyn_item);
+    if (dyn_item)
+    {
+        OFCHECK(dyn_item->setTableSpeed(1.0).good());
+        OFCHECK(dyn_item->setTableFeedPerRotation(0.1).good());
+        OFCHECK(dyn_item->setSpiralPitchFactor(0.2).good());
+        dyn.getCTTableDynamicsItems().push_back(dyn_item);
+    }
+
+    FGCTPosition pos;
+    OFCHECK(pos.setTablePosition(100.0).good());
+    OFCHECK(pos.setReconstructionTargetCenterPatient(OFVector<Float64>(3, 1.0)).good());
+    OFCHECK(pos.setDataCollectionCenterPatient(OFVector<Float64>(3, 2.0)).good());
+
+    FGCTGeometry geo;
+    FGCTGeometry::FGCTGeometryItem* geo_item = new FGCTGeometry::FGCTGeometryItem;
+    if (geo_item)
+    {
+        OFCHECK(geo_item->setDistanceSourceToDataCollectionCenter(5.0).good());
+        OFCHECK(geo_item->setDistanceSourceToDetector(0.5).good());
+        geo.getCTGeometryItems().push_back(geo_item);
+    }
+
+    FGCTReconstruction rec;
+    OFCHECK(rec.setConvolutionKernel("DUMMY").good());
+    OFCHECK(rec.setConvolutionKernelGroup("DUMMYGROUP").good());
+    OFCHECK(rec.setImageFilter("FILTER").good());
+    OFCHECK(rec.setReconstructionAlgorithm("ALGO").good());
+    OFCHECK(rec.setReconstructionAngle(90.0).good());
+    OFCHECK(rec.setReconstructionDiameter(100.0).good());
+    // Not permitted if Reconstruction Diameter is provided instead
+    // OFCHECK(rec.setReconstructionFieldOfView(100.0, 100.0).good());
+    OFCHECK(rec.setReconstructionPixelSpacing(0.1, 0.1).good());
+
+    FGCTExposure exp;
+    FGCTExposure::FGCTExposureItem* exp_item = new FGCTExposure::FGCTExposureItem;
+    if (exp_item)
+    {
+        OFCHECK(exp_item->setCTDIVol(0.1).good());
+        CodeSequenceMacro* phantom_item = new CodeSequenceMacro("113682", "DCM", "ACR Accreditation Phantom - CT");
+        exp_item->getCTDIPhantomTypeCodeSequence().push_back(phantom_item);
+        OFCHECK(exp_item->setEstimatedDoseSaving(0.2).good());
+        OFCHECK(exp_item->setExposureInMas(0.3).good());
+        OFCHECK(exp_item->setExposureModulationType("WEIRD").good());
+        OFCHECK(exp_item->setExposureTimeInMs(0.4).good());
+        OFCHECK(exp_item->setImageAndFluoroscopyAreaDoseProduct(0.5).good());
+        OFCHECK(exp_item->setWaterEquivalentDiameter(0.6).good());
+        CodeSequenceMacro* water_code = new CodeSequenceMacro("113987", "DCM", "AAPM 220");
+        exp_item->getWaterEquivalentDiameterCalculationMethodCodeSequence().push_back(water_code);
+        OFCHECK(exp_item->setXRayTubeCurrentInMa(0.7).good());
+        exp.getCTExposureItems().push_back(exp_item);
+    }
+
+    FGCTXRayDetails det;
+    FGCTXRayDetails::FGCTXRayDetailsItem* det_item = new FGCTXRayDetails::FGCTXRayDetailsItem;
+    if (det_item)
+    {
+        OFCHECK(det_item->setCalciumScoringMassFactorDevice(OFVector<Float32>(3, 1)).good());
+        OFCHECK(det_item->setCalciumScoringMassFactorPatient(2).good());
+        OFCHECK(det_item->setEnergyWeightingFactor(3).good());
+        OFCHECK(det_item->setFilterMaterial("FILTER_MATERIAL").good());
+        OFCHECK(det_item->setFilterType("FILTER_TYPE").good());
+        OFCHECK(det_item->setFocalSpots(OFVector<Float64>(4, 4.4)).good());
+        OFCHECK(det_item->setKVP(5.0).good());
+        det.getCTXRayDetailsItems().push_back(det_item);
+    }
+
+    FGPixelValueTransformation trans;
+    trans.setFGType(FGPixelValueTransformation::E_PixelValTrans_CT);
+    trans.setRescaleIntercept("0");
+    trans.setRescaleSlope("1");
+    trans.setRescaleType("HU");
+
+    FGCTAdditionalXRaySource asrc;
+    FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem* asrc_item
+        = new FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem;
+    if (asrc_item)
+    {
+        OFCHECK(asrc_item->setDataCollectionDiameter(1.0).good());
+        OFCHECK(asrc_item->setEnergyWeightingFactor(2.0).good());
+        OFCHECK(asrc_item->setExposureInmAs(3.0).good());
+        OFCHECK(asrc_item->setFilterMaterial("FILTER_MATERIAL").good());
+        OFCHECK(asrc_item->setFilterType("FILTER_TYPE").good());
+        OFCHECK(asrc_item->setFocalSpots(OFVector<Float64>(4, 4.4)).good());
+        OFCHECK(asrc_item->setKVP(5).good());
+        OFCHECK(asrc_item->setXRayTubeCurrentInmA(6).good());
+        asrc.getCTAdditionalXRaySourceItems().push_back(asrc_item);
+    }
+
+    FGTemporalPosition tempos;
+    OFCHECK(tempos.setTemporalPositionTimeOffset(1.0).good());
+
+    OFCHECK(ct->addForAllFrames(meas).good());
+    OFCHECK(ct->addForAllFrames(planpo).good());
+    OFCHECK(ct->addForAllFrames(planor).good());
+    OFCHECK(ct->addForAllFrames(ana).good());
+    OFCHECK(ct->addForAllFrames(voi).good());
+    OFCHECK(ct->addForAllFrames(irr).good());
+    OFCHECK(ct->addForAllFrames(itype).good());
+    OFCHECK(ct->addForAllFrames(atype).good());
+    OFCHECK(ct->addForAllFrames(adetails).good());
+    OFCHECK(ct->addForAllFrames(dyn).good());
+    OFCHECK(ct->addForAllFrames(pos).good());
+    OFCHECK(ct->addForAllFrames(geo).good());
+    OFCHECK(ct->addForAllFrames(rec).good());
+    OFCHECK(ct->addForAllFrames(exp).good());
+    OFCHECK(ct->addForAllFrames(det).good());
+    OFCHECK(ct->addForAllFrames(trans).good());
+    OFCHECK(ct->addForAllFrames(asrc).good());
+    OFCHECK(ct->addForAllFrames(tempos).good());
+}
+
+static void addFrames(EctEnhancedCT* ct)
+{
+    if (!ct)
+        return;
+
+    FGFrameContent* fg = new FGFrameContent();
+    fg->setStackID("1");
+    OFCHECK(fg);
+    if (fg)
+    {
+        EctEnhancedCT::FramesType frames = ct->getFrames();
+        for (Uint16 frameNo = 1; frameNo <= NUM_FRAMES; frameNo++)
+        {
+            OFCHECK(fg->setFrameAcquisitionNumber(frameNo).good());
+            OFCHECK(fg->setFrameReferenceDateTime("20190816092557").good());
+            OFCHECK(fg->setFrameAcquisitionDateTime("20190816092557").good());
+            OFCHECK(fg->setFrameAcquisitionDuration(0.001).good());
+            OFCHECK(fg->setInStackPositionNumber(frameNo).good());
+            OFCHECK(fg->setDimensionIndexValues(1, 0).good());
+            OFCHECK(fg->setDimensionIndexValues(frameNo, 1).good());
+            OFVector<FGBase*> groups;
+            groups.push_back(fg);
+
+            Uint16* data = new Uint16[NUM_PIXELS_PER_FRAME];
+            for (size_t i = 0; i < NUM_PIXELS_PER_FRAME; ++i)
+            {
+                data[i] = frameNo;
+            }
+            OFCHECK(
+                OFget<EctEnhancedCT::Frames<Uint16> >(&frames)->addFrame(data, NUM_PIXELS_PER_FRAME, groups).good());
+            delete[] data;
+        }
+    }
+    delete fg;
+}
+
+static void addDimensions(EctEnhancedCT* ct)
+{
+    if (!ct)
+        return;
+    IODMultiframeDimensionModule& dims = ct->getDimensions();
+    OFCHECK(dims.addDimensionIndex(
+                    DCM_StackID, "2.25.30855560781715986879861690673941231222", DCM_FrameContentSequence, "STACK_DIM")
+                .good());
+    OFCHECK(dims.addDimensionIndex(DCM_InStackPositionNumber,
+                                   "2.25.30855560781715986879861690673941231222",
+                                   DCM_FrameContentSequence,
+                                   "STACK_DIM")
+                .good());
+    OFunique_ptr<IODMultiframeDimensionModule::DimensionOrganizationItem> org(
+        new IODMultiframeDimensionModule::DimensionOrganizationItem);
+    if (org)
+    {
+        org->setDimensionOrganizationUID("2.25.30855560781715986879861690673941231222");
+        dims.getDimensionOrganizationSequence().push_back(org.release());
+    }
+}
+
+static void writeAndCheckConcatenation(EctEnhancedCT* ct, OFList<OFFilename>& concats)
+{
+    ConcatenationCreator cc;
+    cc.setCfgFramesPerInstance(NUM_FRAMES_CONCAT);
+    OFCHECK(ct->writeConcatenation(cc).good());
+    size_t numInstances = cc.getNumInstances();
+    OFCHECK(numInstances == NUM_FRAMES);
+    OFCondition result;
+    for (size_t n = 0; n < numInstances; n++)
+    {
+        OFStringStream s;
+        s << "concat_" << n << "_";
+        OFTempFile tf(O_RDWR, "", s.str().c_str(), ".dcm");
+        result = cc.writeNextInstance(tf.getFilename());
+        OFCHECK(result.good());
+        if (result.good())
+        {
+            DcmFileFormat concat;
+            OFCHECK(concat.loadFile(tf.getFilename()).good());
+            checkConcatenationInstance(n, ct, concat.getDataset());
+            concats.push_back(tf.getFilename());
+            tf.stealFile();
+        }
+    }
+}
+
+static void checkConcatenationInstance(size_t numInstance, EctEnhancedCT* srcInstance, DcmDataset* concatInstance)
+{
+    EctEnhancedCT* concat = NULL;
+    OFCondition result = EctEnhancedCT::loadDataset(*concatInstance, concat);
+    OFCHECK(result.good());
+    if ((concat == NULL )|| result.bad()) return;
+
+    size_t numFrames;
+    numFrames = concat->getNumberOfFrames();
+    OFCHECK(numFrames == 1);
+    IODMultiFrameFGModule::ConcatenationInfo& ci = concat->getConcatenationInfo();
+    OFString val;
+    OFCHECK(ci.getConcatenationUID(val).good());
+    OFCHECK(DcmUniqueIdentifier::checkStringValue(val, "1").good());
+    Uint32 frameOffsetNo = 0;
+    OFCHECK(ci.getConcatenationFrameOffsetNumber(frameOffsetNo).good());
+    OFCHECK(frameOffsetNo == numInstance);
+    Uint16 inConcatNo = 0;
+    OFCHECK(ci.getInConcatenationNumber(inConcatNo).good());
+    OFCHECK(inConcatNo == numInstance + 1);
+    Uint16 concatTotalNo = 0;
+    OFCHECK(ci.getInConcatenationTotalNumber(concatTotalNo).good());
+    OFCHECK(concatTotalNo == NUM_FRAMES);
+
+    OFString srcUID;
+    OFCHECK(ci.getSOPInstanceUIDOfConcatenationSource(srcUID).good());
+    OFCHECK(srcInstance->getSOPCommon().getSOPInstanceUID(val).good());
+    OFCHECK(srcUID == val);
+
+    OFCHECK(concat->getSOPCommon().getSOPInstanceUID(val).good());
+    OFCHECK(srcUID != val);
+
+    FunctionalGroups::const_iterator srcShared = srcInstance->getFunctionalGroups().getShared()->begin();
+    FunctionalGroups::const_iterator cShared   = concat->getFunctionalGroups().getShared()->begin();
+    size_t numShared                           = 0;
+    do
+    {
+        OFCHECK(srcShared->second->compare(*cShared->second) == 0);
+        srcShared++;
+        cShared++;
+        numShared++;
+    } while ((srcShared != srcInstance->getFunctionalGroups().getShared()->end())
+             && (cShared != concat->getFunctionalGroups().getShared()->end()));
+    OFCHECK((srcShared == srcInstance->getFunctionalGroups().getShared()->end())
+            && (cShared == concat->getFunctionalGroups().getShared()->end()));
+    DcmSequenceOfItems* cPerFrame = NULL;
+    result = concatInstance->findAndGetSequence(DCM_PerFrameFunctionalGroupsSequence, cPerFrame);
+    OFCHECK(result.good());
+    if ((cPerFrame == NULL) || result.bad()) return;
+    OFCHECK(cPerFrame->card() == 1);
+
+    OFBool perFrame = OFFalse;
+    FGBase* fg      = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTACQUISITIONDETAILS, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTACQUISITIONTYPE, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTADDITIONALXRAYSOURCE, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTEXPOSURE, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTGEOMETRY, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTIMAGEFRAMETYPE, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTPOSITION, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTRECONSTRUCTION, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTTABLEDYNAMICS, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTXRAYDETAILS, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTXRAYDETAILS, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_FRAMECONTENT, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFTrue);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_FRAMEANATOMY, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_FRAMEANATOMY, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_FRAMEVOILUTMETA, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_FRAMEANATOMY, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_IRRADIATIONEVENTIDENT, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_PIXELVALUETRANSMETA, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_IRRADIATIONEVENTIDENT, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = NULL;
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_PIXELMEASURES, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = NULL;
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_PLANEPOSPATIENT, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = NULL;
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_PLANEORIENTPATIENT, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_TEMPORALPOSITION, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    EctEnhancedCT::FramesType frames = concat->getFrames();
+    Uint16* frame                    = OFget<EctEnhancedCT::Frames<Uint16> >(&frames)->getFrame(0);
+    OFCHECK(frame != OFnullptr);
+    // Check that all pixels are set to their original source instances frame number (starting from 1)
+    for (size_t pix = 0; pix < NUM_PIXELS_PER_FRAME; pix++)
+    {
+        OFCHECK(frame[pix] == numInstance + 1);
+    }
+    delete concat;
+}
+
+void loadAndCheckConcatenation(const OFList<OFFilename>& concats)
+{
+    ConcatenationLoader cl;
+    OFCondition result = cl.scan(concats);
+    OFCHECK(result.good());
+    if (result.good())
+    {
+        DcmDataset merged;
+        EctEnhancedCT* mergedCT = NULL;
+        result                  = EctEnhancedCT::loadConcatenation(cl, cl.getInfo().begin()->first, mergedCT);
+        if (result.good())
+        {
+            ConcatenationCreator cc;
+            cc.setCfgFramesPerInstance(1);
+            result = mergedCT->writeConcatenation(cc);
+            OFCHECK(result.good());
+            if (result.good())
+            {
+                DcmDataset d;
+                result = cc.writeNextInstance(d);
+                if (result.good())
+                {
+                    // patch in expected timestamp and instance UIDs to match dump
+                    OFCHECK(d.putAndInsertOFStringArray(DCM_ContentDate, "20190816").good());
+                    OFCHECK(d.putAndInsertOFStringArray(DCM_ContentTime, "092557").good());
+                    OFCHECK(d.putAndInsertOFStringArray(DCM_SOPInstanceUID,
+                                                        "1.2.276.0.7230010.3.1.4.8323329.21580.1571390622.913190")
+                                .good());
+                    OFCHECK(d.putAndInsertOFStringArray(DCM_ConcatenationUID,
+                                                        "1.2.276.0.7230010.3.1.4.8323329.23689.1571391649.103636")
+                                .good());
+                    OFStringStream s;
+                    d.print(s, DCMTypes::PF_shortenLongTagValues);
+                    checkCreatedObject(s.str().c_str());
+                    checkConcatenationInstance(0, mergedCT, &d);
+                }
+            }
+            delete mergedCT;
+        }
+    }
+}
+
+static void prepareExpectedDump()
+{
+    EXPECTED_DUMP += "\n";
+    EXPECTED_DUMP += "# Dicom-Data-Set\n";
+    EXPECTED_DUMP += "# Used TransferSyntax: Little Endian Explicit\n";
+    EXPECTED_DUMP += "(0008,0008) CS [ORIGINAL\\PRIMARY\\VOLUME\\MAXIMUM]        #  32, 4 ImageType\n";
+    EXPECTED_DUMP += "(0008,0016) UI =EnhancedCTImageStorage                  #  28, 1 SOPClassUID\n";
+    EXPECTED_DUMP
+        += "(0008,0018) UI [1.2.276.0.7230010.3.1.4.8323329.21580.1571390622.913190] #  56, 1 SOPInstanceUID\n";
+    EXPECTED_DUMP += "(0008,0020) DA [20190801]                               #   8, 1 StudyDate\n";
+    EXPECTED_DUMP += "(0008,0023) DA [20190816]                               #   8, 1 ContentDate\n";
+    EXPECTED_DUMP += "(0008,002a) DT [20190801120000]                         #  14, 1 AcquisitionDateTime\n";
+    EXPECTED_DUMP += "(0008,0030) TM [120000]                                 #   6, 1 StudyTime\n";
+    EXPECTED_DUMP += "(0008,0033) TM [092557]                                 #   6, 1 ContentTime\n";
+    EXPECTED_DUMP += "(0008,0050) SH (no value available)                     #   0, 0 AccessionNumber\n";
+    EXPECTED_DUMP += "(0008,0060) CS [CT]                                     #   2, 1 Modality\n";
+    EXPECTED_DUMP += "(0008,0070) LO [Open Connections]                       #  16, 1 Manufacturer\n";
+    EXPECTED_DUMP += "(0008,0090) PN (no value available)                     #   0, 0 ReferringPhysicianName\n";
+    EXPECTED_DUMP += "(0008,103e) LO [Test Description]                       #  16, 1 SeriesDescription\n";
+    EXPECTED_DUMP += "(0008,1090) LO [OC CT]                                  #   6, 1 ManufacturerModelName\n";
+    EXPECTED_DUMP += "(0008,9205) CS [MONOCHROME]                             #  10, 1 PixelPresentation\n";
+    EXPECTED_DUMP += "(0008,9206) CS [VOLUME]                                 #   6, 1 VolumetricProperties\n";
+    EXPECTED_DUMP
+        += "(0008,9207) CS [VOLUME_RENDER]                          #  14, 1 VolumeBasedCalculationTechnique\n";
+    EXPECTED_DUMP += "(0010,0010) PN [Bond^James]                             #  10, 1 PatientName\n";
+    EXPECTED_DUMP += "(0010,0020) LO [007]                                    #   4, 1 PatientID\n";
+    EXPECTED_DUMP += "(0010,0030) DA [19771007]                               #   8, 1 PatientBirthDate\n";
+    EXPECTED_DUMP += "(0010,0040) CS (no value available)                     #   0, 0 PatientSex\n";
+    EXPECTED_DUMP += "(0010,1010) AS [040Y]                                   #   4, 1 PatientAge\n";
+    EXPECTED_DUMP += "(0018,1000) LO [4711]                                   #   4, 1 DeviceSerialNumber\n";
+    EXPECTED_DUMP += "(0018,1020) LO [0.1]                                    #   4, 1 SoftwareVersions\n";
+    EXPECTED_DUMP += "(0018,5100) CS [HFS]                                    #   4, 1 PatientPosition\n";
+    EXPECTED_DUMP += "(0018,9004) CS [RESEARCH]                               #   8, 1 ContentQualification\n";
+    EXPECTED_DUMP += "(0018,9073) FD 2                                        #   8, 1 AcquisitionDuration\n";
+    EXPECTED_DUMP
+        += "(0020,000d) UI [1.2.276.0.7230010.3.1.2.8323329.14863.1565940357.864811] #  56, 1 StudyInstanceUID\n";
+    EXPECTED_DUMP
+        += "(0020,000e) UI [1.2.276.0.7230010.3.1.3.8323329.14863.1565940357.864812] #  56, 1 SeriesInstanceUID\n";
+    EXPECTED_DUMP += "(0020,0010) SH [1]                                      #   2, 1 StudyID\n";
+    EXPECTED_DUMP += "(0020,0011) IS [1]                                      #   2, 1 SeriesNumber\n";
+    EXPECTED_DUMP += "(0020,0013) IS [1]                                      #   2, 1 InstanceNumber\n";
+    EXPECTED_DUMP += "(0020,0052) UI [2.25.30853397773651184949181049330553108086] #  44, 1 FrameOfReferenceUID\n";
+    EXPECTED_DUMP += "(0020,0242) UI [1.2.276.0.7230010.3.1.4.8323329.14863.1565940357.864813] #  56, 1 "
+                     "SOPInstanceUIDOfConcatenationSource\n";
+    EXPECTED_DUMP += "(0020,1040) LO (no value available)                     #   0, 0 PositionReferenceIndicator\n";
+    EXPECTED_DUMP
+        += "(0020,9161) UI [1.2.276.0.7230010.3.1.4.8323329.23689.1571391649.103636] #  56, 1 ConcatenationUID\n";
+    EXPECTED_DUMP += "(0020,9162) US 1                                        #   2, 1 InConcatenationNumber\n";
+    EXPECTED_DUMP += "(0020,9163) US $InConcatenationTotalNumber#   2, 1 InConcatenationTotalNumber\n";
+    EXPECTED_DUMP += "(0020,9221) SQ (Sequence with explicit length #=1)      #   0, 1 DimensionOrganizationSequence\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "    (0020,9164) UI [2.25.30855560781715986879861690673941231222] #  44, 1 DimensionOrganizationUID\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "(0020,9222) SQ (Sequence with explicit length #=2)      #   0, 1 DimensionIndexSequence\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=4)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "    (0020,9164) UI [2.25.30855560781715986879861690673941231222] #  44, 1 DimensionOrganizationUID\n";
+    EXPECTED_DUMP += "    (0020,9165) AT (0020,9056)                              #   4, 1 DimensionIndexPointer\n";
+    EXPECTED_DUMP += "    (0020,9167) AT (0020,9111)                              #   4, 1 FunctionalGroupPointer\n";
+    EXPECTED_DUMP += "    (0020,9421) LO [STACK_DIM]                              #  10, 1 DimensionDescriptionLabel\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=4)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "    (0020,9164) UI [2.25.30855560781715986879861690673941231222] #  44, 1 DimensionOrganizationUID\n";
+    EXPECTED_DUMP += "    (0020,9165) AT (0020,9057)                              #   4, 1 DimensionIndexPointer\n";
+    EXPECTED_DUMP += "    (0020,9167) AT (0020,9111)                              #   4, 1 FunctionalGroupPointer\n";
+    EXPECTED_DUMP += "    (0020,9421) LO [STACK_DIM]                              #  10, 1 DimensionDescriptionLabel\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "(0020,9228) UL 0                                        #   4, 1 ConcatenationFrameOffsetNumber\n";
+    EXPECTED_DUMP += "(0028,0002) US 1                                        #   2, 1 SamplesPerPixel\n";
+    EXPECTED_DUMP += "(0028,0004) CS [MONOCHROME2]                            #  12, 1 PhotometricInterpretation\n";
+    EXPECTED_DUMP += "(0028,0008) IS [1]                                      #   2, 1 NumberOfFrames\n";
+    EXPECTED_DUMP += "(0028,0010) US $Rows#   2, 1 Rows\n";
+    EXPECTED_DUMP += "(0028,0011) US $Columns#   2, 1 Columns\n";
+    EXPECTED_DUMP += "(0028,0100) US 16                                       #   2, 1 BitsAllocated\n";
+    EXPECTED_DUMP += "(0028,0101) US 16                                       #   2, 1 BitsStored\n";
+    EXPECTED_DUMP += "(0028,0102) US 15                                       #   2, 1 HighBit\n";
+    EXPECTED_DUMP += "(0028,0103) US 0                                        #   2, 1 PixelRepresentation\n";
+    EXPECTED_DUMP += "(0028,0301) CS [NO]                                     #   2, 1 BurnedInAnnotation\n";
+    EXPECTED_DUMP += "(0028,2110) CS [00]                                     #   2, 1 LossyImageCompression\n";
+    EXPECTED_DUMP += "(0040,0555) SQ (Sequence with explicit length #=0)      #   0, 1 AcquisitionContextSequence\n";
+    EXPECTED_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "(2050,0020) CS [IDENTITY]                               #   8, 1 PresentationLUTShape\n";
+    EXPECTED_DUMP
+        += "(5200,9229) SQ (Sequence with explicit length #=1)      #   0, 1 SharedFunctionalGroupsSequence\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=18)         #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0018,9301) SQ (Sequence with explicit length #=1)      #   0, 1 CTAcquisitionTypeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=4)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0018,9302) CS [CONSTANT_ANGLE]                         #  14, 1 AcquisitionType\n";
+    EXPECTED_DUMP += "        (0018,9303) FD 0.1                                      #   8, 1 TubeAngle\n";
+    EXPECTED_DUMP += "        (0018,9333) CS [YES]                                    #   4, 1 ConstantVolumeFlag\n";
+    EXPECTED_DUMP += "        (0018,9334) CS [NO]                                     #   2, 1 FluoroscopyFlag\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "    (0018,9304) SQ (Sequence with explicit length #=1)      #   0, 1 CTAcquisitionDetailsSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,0090) DS [20]                                     #   2, 1 DataCollectionDiameter\n";
+    EXPECTED_DUMP += "        (0018,1120) DS [5]                                      #   2, 1 GantryDetectorTilt\n";
+    EXPECTED_DUMP += "        (0018,1130) DS [50]                                     #   2, 1 TableHeight\n";
+    EXPECTED_DUMP += "        (0018,1140) CS [CW]                                     #   2, 1 RotationDirection\n";
+    EXPECTED_DUMP += "        (0018,9305) FD 5                                        #   8, 1 RevolutionTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9306) FD 1                                        #   8, 1 SingleCollimationWidth\n";
+    EXPECTED_DUMP += "        (0018,9307) FD 10                                       #   8, 1 TotalCollimationWidth\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0018,9308) SQ (Sequence with explicit length #=1)      #   0, 1 CTTableDynamicsSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0018,9309) FD 1                                        #   8, 1 TableSpeed\n";
+    EXPECTED_DUMP += "        (0018,9310) FD 0.1                                      #   8, 1 TableFeedPerRotation\n";
+    EXPECTED_DUMP += "        (0018,9311) FD 0.2                                      #   8, 1 SpiralPitchFactor\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0018,9312) SQ (Sequence with explicit length #=1)      #   0, 1 CTGeometrySequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=2)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,1110) DS [0.5]                                    #   4, 1 DistanceSourceToDetector\n";
+    EXPECTED_DUMP += "        (0018,9335) FD 5                                        #   8, 1 "
+                     "DistanceSourceToDataCollectionCenter\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0018,9314) SQ (Sequence with explicit length #=1)      #   0, 1 CTReconstructionSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,1100) DS [100]                                    #   4, 1 ReconstructionDiameter\n";
+    EXPECTED_DUMP += "        (0018,1210) SH [DUMMY]                                  #   6, 1 ConvolutionKernel\n";
+    EXPECTED_DUMP
+        += "        (0018,9315) CS [ALGO]                                   #   4, 1 ReconstructionAlgorithm\n";
+    EXPECTED_DUMP
+        += "        (0018,9316) CS [DUMMYGROUP]                             #  10, 1 ConvolutionKernelGroup\n";
+    EXPECTED_DUMP += "        (0018,9319) FD 90                                       #   8, 1 ReconstructionAngle\n";
+    EXPECTED_DUMP += "        (0018,9320) SH [FILTER]                                 #   6, 1 ImageFilter\n";
+    EXPECTED_DUMP
+        += "        (0018,9322) FD 0.1\\0.1                                  #  16, 2 ReconstructionPixelSpacing\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0018,9321) SQ (Sequence with explicit length #=1)      #   0, 1 CTExposureSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=10)         #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0018,115e) DS [0.5]                                    #   4, 1 "
+                     "ImageAndFluoroscopyAreaDoseProduct\n";
+    EXPECTED_DUMP
+        += "        (0018,1271) FD 0.6                                      #   8, 1 WaterEquivalentDiameter\n";
+    EXPECTED_DUMP += "        (0018,1272) SQ (Sequence with explicit length #=1)      #   0, 1 "
+                     "WaterEquivalentDiameterCalculationMethodCodeSequence\n";
+    EXPECTED_DUMP += "          (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "            (0008,0100) SH [113987]                                 #   6, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "            (0008,0102) SH [DCM]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "            (0008,0104) LO [AAPM 220]                               #   8, 1 CodeMeaning\n";
+    EXPECTED_DUMP
+        += "          (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP
+        += "        (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "        (0018,9323) CS [WEIRD]                                  #   6, 1 ExposureModulationType\n";
+    EXPECTED_DUMP += "        (0018,9324) FD 0.2                                      #   8, 1 EstimatedDoseSaving\n";
+    EXPECTED_DUMP += "        (0018,9328) FD 0.4                                      #   8, 1 ExposureTimeInms\n";
+    EXPECTED_DUMP += "        (0018,9330) FD 0.7                                      #   8, 1 XRayTubeCurrentInmA\n";
+    EXPECTED_DUMP += "        (0018,9332) FD 0.3                                      #   8, 1 ExposureInmAs\n";
+    EXPECTED_DUMP += "        (0018,9345) FD 0.1                                      #   8, 1 CTDIvol\n";
+    EXPECTED_DUMP
+        += "        (0018,9346) SQ (Sequence with explicit length #=1)      #   0, 1 CTDIPhantomTypeCodeSequence\n";
+    EXPECTED_DUMP += "          (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "            (0008,0100) SH [113682]                                 #   6, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "            (0008,0102) SH [DCM]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "            (0008,0104) LO [ACR Accreditation Phantom - CT]         #  30, 1 CodeMeaning\n";
+    EXPECTED_DUMP
+        += "          (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP
+        += "        (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0018,9325) SQ (Sequence with explicit length #=1)      #   0, 1 CTXRayDetailsSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0018,0060) DS [5]                                      #   2, 1 KVP\n";
+    EXPECTED_DUMP += "        (0018,1160) SH [FILTER_TYPE]                            #  12, 1 FilterType\n";
+    EXPECTED_DUMP += "        (0018,1190) DS [4.4\\4.4\\4.4\\4.4]                        #  16, 4 FocalSpots\n";
+    EXPECTED_DUMP += "        (0018,7050) CS [FILTER_MATERIAL]                        #  16, 1 FilterMaterial\n";
+    EXPECTED_DUMP
+        += "        (0018,9351) FL 2                                        #   4, 1 CalciumScoringMassFactorPatient\n";
+    EXPECTED_DUMP += "        (0018,9352) FL 1\\1\\1                                    #  12, 3 "
+                     "CalciumScoringMassFactorDevice\n";
+    EXPECTED_DUMP += "        (0018,9353) FL 3                                        #   4, 1 EnergyWeightingFactor\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0018,9326) SQ (Sequence with explicit length #=1)      #   0, 1 CTPositionSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,9313) FD 2\\2\\2                                    #  24, 3 DataCollectionCenterPatient\n";
+    EXPECTED_DUMP += "        (0018,9318) FD 1\\1\\1                                    #  24, 3 "
+                     "ReconstructionTargetCenterPatient\n";
+    EXPECTED_DUMP += "        (0018,9327) FD 100                                      #   8, 1 TablePosition\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0018,9329) SQ (Sequence with explicit length #=1)      #   0, 1 CTImageFrameTypeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=4)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,9007) CS [ORIGINAL\\PRIMARY\\VOLUME\\MAXIMUM]        #  32, 4 FrameType\n";
+    EXPECTED_DUMP += "        (0008,9205) CS [MONOCHROME]                             #  10, 1 PixelPresentation\n";
+    EXPECTED_DUMP += "        (0008,9206) CS [VOLUME]                                 #   6, 1 VolumetricProperties\n";
+    EXPECTED_DUMP
+        += "        (0008,9207) CS [VOLUME_RENDER]                          #  14, 1 VolumeBasedCalculationTechnique\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "    (0018,9360) SQ (Sequence with explicit length #=1)      #   0, 1 CTAdditionalXRaySourceSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=8)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0018,0060) DS [5]                                      #   2, 1 KVP\n";
+    EXPECTED_DUMP
+        += "        (0018,0090) DS [1]                                      #   2, 1 DataCollectionDiameter\n";
+    EXPECTED_DUMP += "        (0018,1160) SH [FILTER_TYPE]                            #  12, 1 FilterType\n";
+    EXPECTED_DUMP += "        (0018,1190) DS [4.4\\4.4\\4.4\\4.4]                        #  16, 4 FocalSpots\n";
+    EXPECTED_DUMP += "        (0018,7050) CS [FILTER_MATERIAL]                        #  16, 1 FilterMaterial\n";
+    EXPECTED_DUMP += "        (0018,9330) FD 6                                        #   8, 1 XRayTubeCurrentInmA\n";
+    EXPECTED_DUMP += "        (0018,9332) FD 3                                        #   8, 1 ExposureInmAs\n";
+    EXPECTED_DUMP += "        (0018,9353) FL 2                                        #   4, 1 EnergyWeightingFactor\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0018,9477) SQ (Sequence with explicit length #=1)      #   0, 1 "
+                     "IrradiationEventIdentificationSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0008,3010) UI [2.25.30853892236613436472911970638347155062] #  44, 1 IrradiationEventUID\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0020,9071) SQ (Sequence with explicit length #=1)      #   0, 1 FrameAnatomySequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=2)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0008,2218) SQ (Sequence with explicit length #=1)      #   0, 1 AnatomicRegionSequence\n";
+    EXPECTED_DUMP += "          (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "            (0008,0100) SH [12738006]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "            (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "            (0008,0104) LO [Brain]                                  #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP
+        += "          (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP
+        += "        (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "        (0020,9072) CS [B]                                      #   2, 1 FrameLaterality\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0020,9113) SQ (Sequence with explicit length #=1)      #   0, 1 PlanePositionSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0020,0032) DS [0.0\\0.0\\0.0]                            #  12, 3 ImagePositionPatient\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0020,9116) SQ (Sequence with explicit length #=1)      #   0, 1 PlaneOrientationSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0020,0037) DS [1.0\\0.0\\0.0\\0.0\\1.0\\0.0]                #  24, 6 ImageOrientationPatient\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0020,9310) SQ (Sequence with explicit length #=1)      #   0, 1 TemporalPositionSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0020,930d) FD 1                                        #   8, 1 TemporalPositionTimeOffset\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0028,9110) SQ (Sequence with explicit length #=1)      #   0, 1 PixelMeasuresSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0018,0050) DS [1.0]                                    #   4, 1 SliceThickness\n";
+    EXPECTED_DUMP += "        (0018,0088) DS [0.05]                                   #   4, 1 SpacingBetweenSlices\n";
+    EXPECTED_DUMP += "        (0028,0030) DS [0.1\\0.1]                                #   8, 2 PixelSpacing\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0028,9132) SQ (Sequence with explicit length #=1)      #   0, 1 FrameVOILUTSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0028,1050) DS [1000]                                   #   4, 1 WindowCenter\n";
+    EXPECTED_DUMP += "        (0028,1051) DS [2000]                                   #   4, 1 WindowWidth\n";
+    EXPECTED_DUMP
+        += "        (0028,1055) LO [BRAIN]                                  #   6, 1 WindowCenterWidthExplanation\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "    (0028,9145) SQ (Sequence with explicit length #=1)      #   0, 1 PixelValueTransformationSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0028,1052) DS [0]                                      #   2, 1 RescaleIntercept\n";
+    EXPECTED_DUMP += "        (0028,1053) DS [1]                                      #   2, 1 RescaleSlope\n";
+    EXPECTED_DUMP += "        (0028,1054) LO [HU]                                     #   2, 1 RescaleType\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "(5200,9230) SQ (Sequence with explicit length #=1)      #   0, 1 PerFrameFunctionalGroupsSequence\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0020,9111) SQ (Sequence with explicit length #=1)      #   0, 1 FrameContentSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,9074) DT [20190816092557]                         #  14, 1 FrameAcquisitionDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9151) DT [20190816092557]                         #  14, 1 FrameReferenceDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9220) FD 0.001                                    #   8, 1 FrameAcquisitionDuration\n";
+    EXPECTED_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    EXPECTED_DUMP += "        (0020,9057) UL 1                                        #   4, 1 InStackPositionNumber\n";
+    EXPECTED_DUMP
+        += "        (0020,9156) US 1                                        #   2, 1 FrameAcquisitionNumber\n";
+    EXPECTED_DUMP += "        (0020,9157) UL 1\\1                                      #   8, 2 DimensionIndexValues\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "(7fe0,0010) OW 0001\\0001\\0001\\0001\\0001\\0001\\0001\\0001\\0001\\0001\\0001\\0001\\0001... # "
+                     "32000000, 1 PixelData\n";
+    OFStringStream ss;
+    ss << NUM_ROWS;
+    OFString numRows(ss.str().c_str());
+    size_t spaces = 41 - numRows.length();
+    numRows.append(spaces, ' ');
+    ss.str("");
+    ss << NUM_COLS;
+    OFString numCols(ss.str().c_str());
+    spaces = 41 - numCols.length();
+    numCols.append(spaces, ' ');
+    ss.str("");
+    ss << NUM_FRAMES;
+    OFString numFrames(ss.str().c_str());
+    spaces = 41 - numFrames.length();
+    numFrames.append(spaces, ' ');
+    OFStringUtil::replace_all(EXPECTED_DUMP, "$Rows", numRows);
+    OFStringUtil::replace_all(EXPECTED_DUMP, "$Columns", numCols);
+    OFStringUtil::replace_all(EXPECTED_DUMP, "$InConcatenationTotalNumber", numFrames);
+}
+
+static void checkCreatedObject(const OFString& ds_dump)
+{
+    OFBool dump_ok = (ds_dump == EXPECTED_DUMP);
+    OFCHECK(dump_ok);
+    if (!dump_ok)
+    {
+        CERR << "Dump produced: " << OFendl << ds_dump << OFendl;
+        CERR << "------------------------------------" << OFendl;
+        CERR << "Dump expected: " << OFendl << EXPECTED_DUMP << OFendl;
+        CERR << "------------------------------------" << OFendl;
+    }
+}
diff --git a/dcmect/tests/t_roundtrip.cc b/dcmect/tests/t_roundtrip.cc
new file mode 100644 (file)
index 0000000..3cdeb90
--- /dev/null
@@ -0,0 +1,990 @@
+/*
+ *
+ *  Copyright (C) 2019-2020, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmect
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Tests for creating and loading Enhanced CT objects
+ *
+ */
+
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+
+#include "dcmtk/ofstd/ofmem.h"
+#include "dcmtk/ofstd/ofstrutl.h"
+#include "dcmtk/ofstd/oftempf.h"
+#include "dcmtk/ofstd/oftest.h"
+
+#include "dcmtk/dcmect/enhanced_ct.h"
+
+#include "dcmtk/dcmfg/concatenationcreator.h"
+#include "dcmtk/dcmfg/concatenationloader.h"
+#include "dcmtk/dcmfg/fgctacquisitiondetails.h"
+#include "dcmtk/dcmfg/fgctacquisitiontype.h"
+#include "dcmtk/dcmfg/fgctadditionalxraysource.h"
+#include "dcmtk/dcmfg/fgctexposure.h"
+#include "dcmtk/dcmfg/fgctgeometry.h"
+#include "dcmtk/dcmfg/fgctimageframetype.h"
+#include "dcmtk/dcmfg/fgctposition.h"
+#include "dcmtk/dcmfg/fgctreconstruction.h"
+#include "dcmtk/dcmfg/fgcttabledynamics.h"
+#include "dcmtk/dcmfg/fgctxraydetails.h"
+#include "dcmtk/dcmfg/fgfracon.h"
+#include "dcmtk/dcmfg/fgframeanatomy.h"
+#include "dcmtk/dcmfg/fgframevoilut.h"
+#include "dcmtk/dcmfg/fgirradiationeventid.h"
+#include "dcmtk/dcmfg/fgpixeltransform.h"
+#include "dcmtk/dcmfg/fgpixmsr.h"
+#include "dcmtk/dcmfg/fgplanor.h"
+#include "dcmtk/dcmfg/fgplanpo.h"
+#include "dcmtk/dcmfg/fgrealworldvaluemapping.h"
+#include "dcmtk/dcmfg/fgtemporalposition.h"
+
+static OFLogger tRoundLogger = OFLog::getLogger("dcmtk.test.t_roundtrip");
+
+// Do not change values below since
+// a) The expected dataset (dump) is made for these values
+// b) Total pixel data length in this test must not be bigger than
+//    4 GB, otherwise the calls to writeDataset() will fail.
+// The test dcmect/tests/t_huge_concat.cc allows for exercising
+// "unlimited" pixel data size using writeConcatenation() on all
+// occassions.
+
+static const Uint16 NUM_ROWS             = 2;
+static const Uint16 NUM_COLS             = 2;
+static const Uint16 NUM_FRAMES           = 2;
+static const size_t NUM_PIXELS_PER_FRAME = NUM_COLS * NUM_ROWS;
+static const size_t NUM_FRAMES_CONCAT    = 1;
+
+static OFString EXPECTED_DUMP;
+
+static void prepareExpectedDump();
+static EctEnhancedCT* create();
+static void configureIOD(EctEnhancedCT* ct);
+static void setGenericValues(EctEnhancedCT* ct);
+static void addSharedFGs(EctEnhancedCT* ct);
+static void addFrames(EctEnhancedCT* ct);
+static void addDimensions(EctEnhancedCT* ct);
+static OFString write(EctEnhancedCT* ct, DcmDataset& ds);
+static void checkCreatedObject(const OFString& ds_dump);
+static void writeAndCheckConcatenation(EctEnhancedCT* ct, OFList<OFFilename>& concats);
+static void checkConcatenationInstance(size_t numInstance, EctEnhancedCT* srcInstance, DcmDataset* concatInstance);
+static void loadAndCheckConcatenation(const OFList<OFFilename>& concats);
+
+OFTEST(dcmect_roundtrip)
+{
+    /* make sure data dictionary is loaded */
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK(dcmDataDict.isDictionaryLoaded());
+        return;
+    }
+
+    // Creation
+    EctEnhancedCT* ct = create();
+    configureIOD(ct);
+    setGenericValues(ct);
+    addSharedFGs(ct);
+    addFrames(ct);
+    addDimensions(ct);
+
+    // Write to dataset and compare its dump with expected result
+    DcmFileFormat dcmff;
+    DcmDataset* ds = dcmff.getDataset();
+    prepareExpectedDump();
+    OFString dset_dump = write(ct, *ds);
+    checkCreatedObject(dset_dump);
+
+    // Save to disk, and re-load to test import
+    OFTempFile tf;
+    OFString temp_fn = tf.getFilename();
+    OFCHECK(!temp_fn.empty());
+    OFCHECK(ct->saveFile(temp_fn.c_str(), EXS_LittleEndianExplicit).good());
+
+    // Read object from dataset into EctEnhancedCT object, write again to dataset and
+    // check whether daset before saving to file is identical to object after loading from
+    // disk and writing to dataset
+    delete ct;
+    ct = NULL;
+    ds->clear();
+    OFCHECK(EctEnhancedCT::loadFile(temp_fn, ct).good());
+    OFCHECK(ct != NULL);
+    if (ct)
+    {
+        dset_dump = write(ct, *ds);
+        checkCreatedObject(dset_dump);
+    }
+    OFList<OFFilename> concats;
+    if (ct)
+    {
+        writeAndCheckConcatenation(ct, concats);
+        delete ct;
+    }
+    OFCHECK(!concats.empty());
+    if (!concats.empty())
+    {
+        loadAndCheckConcatenation(concats);
+    }
+    OFListIterator(OFFilename) it = concats.begin();
+    while (it != concats.end())
+    {
+        OFStandard::deleteFile(*it);
+        it++;
+    }
+}
+
+static EctEnhancedCT* create()
+{
+    IODEnhGeneralEquipmentModule::EquipmentInfo eq("Open Connections", "OC CT", "4711", "0.1");
+    EctEnhancedCT* ct = NULL;
+    OFCondition result;
+    result = EctEnhancedCT::create(ct,
+                                   NUM_ROWS,
+                                   NUM_COLS,
+                                   OFFalse,
+                                   EctTypes::E_ImageType1_Original,
+                                   EctTypes::DT_ImageType3_Volume,
+                                   EctTypes::DT_ImageType4_Maximum,
+                                   "1" /* instance number */,
+                                   EctTypes::E_ContQuali_Research,
+                                   EctTypes::E_PixelPres_Monochrome,
+                                   EctTypes::E_VolProps_Volume,
+                                   EctTypes::DT_VolBasedCalcTechnique_VolumeRender,
+                                   eq,
+                                   "20190801120000" /* acquisition date */,
+                                   2.0 /* acquisition duration */);
+
+    OFCHECK(result.good());
+    OFCHECK(ct != OFnullptr);
+    return ct;
+}
+
+static void configureIOD(EctEnhancedCT* ct)
+{
+    if (!ct)
+        return;
+}
+
+static void setGenericValues(EctEnhancedCT* ct)
+{
+    if (!ct)
+        return;
+    OFCHECK(ct->getPatient().setPatientName("Bond^James").good());
+    OFCHECK(ct->getPatient().setPatientID("007").good());
+    OFCHECK(ct->getPatient().setPatientBirthDate("19771007").good());
+    OFCHECK(ct->getStudy().setStudyDate("20190801").good());
+    OFCHECK(ct->getStudy().setStudyTime("120000").good());
+    OFCHECK(ct->getStudy().setStudyID("1").good());
+    OFCHECK(ct->getPatientStudy().setPatientAge("040Y").good());
+    OFCHECK(ct->getSeries().setSeriesDescription("Test Description").good());
+    OFCHECK(ct->getSeries().setSeriesNumber("1").good());
+    OFCHECK(ct->getSeries().setPatientPosition("HFS").good());
+
+    // Those values are usually computed automatically. UIDS are generated and date/times are set to current values.
+    // But in order to compare the "old" dump with the freshly created image attributes, we set some values manually,
+    // so that they are not overwritten with new, automatically created values later.
+    OFCHECK(ct->getStudy().setStudyInstanceUID("1.2.276.0.7230010.3.1.2.8323329.14863.1565940357.864811").good());
+    OFCHECK(ct->getFrameOfReference().setFrameOfReferenceUID("2.25.30853397773651184949181049330553108086").good());
+    OFCHECK(ct->getSeries().setSeriesInstanceUID("1.2.276.0.7230010.3.1.3.8323329.14863.1565940357.864812").good());
+    OFCHECK(ct->getSOPCommon().setSOPInstanceUID("1.2.276.0.7230010.3.1.4.8323329.14863.1565940357.864813").good());
+
+    OFCHECK(ct->getIODMultiFrameFGModule().setContentTime("092557").good());
+    OFCHECK(ct->getIODMultiFrameFGModule().setContentDate("20190816").good());
+}
+
+static void addSharedFGs(EctEnhancedCT* ct)
+{
+    if (!ct)
+        return;
+
+    FGPixelMeasures meas;
+    OFCHECK(meas.setPixelSpacing("0.1\\0.1").good());
+    OFCHECK(meas.setSliceThickness("1.0").good());
+    OFCHECK(meas.setSpacingBetweenSlices("0.05").good());
+
+    FGPlanePosPatient planpo;
+    OFCHECK(planpo.setImagePositionPatient("0.0", "0.0", "0.0").good());
+
+    FGPlaneOrientationPatient planor;
+    OFCHECK(planor.setImageOrientationPatient("1.0", "0.0", "0.0", "0.0", "1.0", "0.0").good());
+
+    FGFrameAnatomy ana;
+    OFCHECK(ana.setLaterality(FGFrameAnatomy::LATERALITY_BOTH).good());
+    OFCHECK(ana.getAnatomy().getAnatomicRegion().set("12738006", "SCT", "Brain").good());
+
+    FGFrameVOILUT voi;
+    OFCHECK(voi.setCenterWidthExplanation(1000, 2000, FGFrameVOILUT::DT_CT_WindowCenterWidthExplanation_Brain).good());
+
+    FGIrradiationEventIdentification irr;
+    OFCHECK(irr.setIrradiationEventUID("2.25.30853892236613436472911970638347155062").good());
+
+    FGCTImageFrameType itype;
+    OFCHECK(itype.setFrameType("ORIGINAL\\PRIMARY\\VOLUME\\MAXIMUM").good());
+    OFCHECK(itype.setPixelPresentation(FGCTImageFrameType::E_PixelPres_Monochrome).good());
+    OFCHECK(itype.setVolumetricProperties(FGCTImageFrameType::E_VolProp_Volume).good());
+    OFCHECK(itype.setVolumeBasedCalculationTechnique(FGCTImageFrameType::DT_VolBasedCalcTechnique_VolumeRender).good());
+
+    FGCTAcquisitionType atype;
+    OFCHECK(atype.setAcquisitionType(FGCTAcquisitionType::DT_AcquisitionType_ConstantAngle).good());
+    OFCHECK(atype.setTubeAngle(0.1).good());
+    OFCHECK(atype.setConstantVolumeFlag(FGCTAcquisitionType::E_ConstVol_Yes).good());
+    OFCHECK(atype.setFluoroscopyFlag(FGCTAcquisitionType::E_Fluoroscopy_No).good());
+
+    FGCTAcquisitionDetails adetails;
+    FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem* item = new FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem();
+    OFCHECK(item->setRotationDirection(FGCTAcquisitionDetails::E_RotationDirection_CW).good());
+    OFCHECK(item->setRevolutionTime(5).good());
+    OFCHECK(item->setSingleCollimationWidth(1).good());
+    OFCHECK(item->setTotalCollimationWidth(10).good());
+    OFCHECK(item->setTableHeight(50).good());
+    OFCHECK(item->setGantryDetectorTilt(5).good());
+    OFCHECK(item->setDataCollectionDiameter(20).good());
+    adetails.getCTAcquisitionDetailsItems().push_back(item);
+
+    FGCTTableDynamics dyn;
+    FGCTTableDynamics::FGCTTableDynamicsItem* dyn_item = new FGCTTableDynamics::FGCTTableDynamicsItem;
+    OFCHECK(dyn_item);
+    if (dyn_item)
+    {
+        OFCHECK(dyn_item->setTableSpeed(1.0).good());
+        OFCHECK(dyn_item->setTableFeedPerRotation(0.1).good());
+        OFCHECK(dyn_item->setSpiralPitchFactor(0.2).good());
+        dyn.getCTTableDynamicsItems().push_back(dyn_item);
+    }
+
+    FGCTPosition pos;
+    OFCHECK(pos.setTablePosition(100.0).good());
+    OFCHECK(pos.setReconstructionTargetCenterPatient(OFVector<Float64>(3, 1.0)).good());
+    OFCHECK(pos.setDataCollectionCenterPatient(OFVector<Float64>(3, 2.0)).good());
+
+    FGCTGeometry geo;
+    FGCTGeometry::FGCTGeometryItem* geo_item = new FGCTGeometry::FGCTGeometryItem;
+    if (geo_item)
+    {
+        OFCHECK(geo_item->setDistanceSourceToDataCollectionCenter(5.0).good());
+        OFCHECK(geo_item->setDistanceSourceToDetector(0.5).good());
+        geo.getCTGeometryItems().push_back(geo_item);
+    }
+
+    FGCTReconstruction rec;
+    OFCHECK(rec.setConvolutionKernel("DUMMY").good());
+    OFCHECK(rec.setConvolutionKernelGroup("DUMMYGROUP").good());
+    OFCHECK(rec.setImageFilter("FILTER").good());
+    OFCHECK(rec.setReconstructionAlgorithm("ALGO").good());
+    OFCHECK(rec.setReconstructionAngle(90.0).good());
+    OFCHECK(rec.setReconstructionDiameter(100.0).good());
+    // Not permitted if Reconstruction Diameter is provided instead
+    // OFCHECK(rec.setReconstructionFieldOfView(100.0, 100.0).good());
+    OFCHECK(rec.setReconstructionPixelSpacing(0.1, 0.1).good());
+
+    FGCTExposure exp;
+    FGCTExposure::FGCTExposureItem* exp_item = new FGCTExposure::FGCTExposureItem;
+    if (exp_item)
+    {
+        OFCHECK(exp_item->setCTDIVol(0.1).good());
+        CodeSequenceMacro* phantom_item = new CodeSequenceMacro("113682", "DCM", "ACR Accreditation Phantom - CT");
+        exp_item->getCTDIPhantomTypeCodeSequence().push_back(phantom_item);
+        OFCHECK(exp_item->setEstimatedDoseSaving(0.2).good());
+        OFCHECK(exp_item->setExposureInMas(0.3).good());
+        OFCHECK(exp_item->setExposureModulationType("WEIRD").good());
+        OFCHECK(exp_item->setExposureTimeInMs(0.4).good());
+        OFCHECK(exp_item->setImageAndFluoroscopyAreaDoseProduct(0.5).good());
+        OFCHECK(exp_item->setWaterEquivalentDiameter(0.6).good());
+        CodeSequenceMacro* water_code = new CodeSequenceMacro("113987", "DCM", "AAPM 220");
+        exp_item->getWaterEquivalentDiameterCalculationMethodCodeSequence().push_back(water_code);
+        OFCHECK(exp_item->setXRayTubeCurrentInMa(0.7).good());
+        exp.getCTExposureItems().push_back(exp_item);
+    }
+
+    FGCTXRayDetails det;
+    FGCTXRayDetails::FGCTXRayDetailsItem* det_item = new FGCTXRayDetails::FGCTXRayDetailsItem;
+    if (det_item)
+    {
+        OFCHECK(det_item->setCalciumScoringMassFactorDevice(OFVector<Float32>(3, 1)).good());
+        OFCHECK(det_item->setCalciumScoringMassFactorPatient(2).good());
+        OFCHECK(det_item->setEnergyWeightingFactor(3).good());
+        OFCHECK(det_item->setFilterMaterial("FILTER_MATERIAL").good());
+        OFCHECK(det_item->setFilterType("FILTER_TYPE").good());
+        OFCHECK(det_item->setFocalSpots(OFVector<Float64>(4, 4.4)).good());
+        OFCHECK(det_item->setKVP(5.0).good());
+        det.getCTXRayDetailsItems().push_back(det_item);
+    }
+
+    FGPixelValueTransformation trans;
+    trans.setFGType(FGPixelValueTransformation::E_PixelValTrans_CT);
+    trans.setRescaleIntercept("0");
+    trans.setRescaleSlope("1");
+    trans.setRescaleType("HU");
+
+    FGCTAdditionalXRaySource asrc;
+    FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem* asrc_item
+        = new FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem;
+    if (asrc_item)
+    {
+        OFCHECK(asrc_item->setDataCollectionDiameter(1.0).good());
+        OFCHECK(asrc_item->setEnergyWeightingFactor(2.0).good());
+        OFCHECK(asrc_item->setExposureInmAs(3.0).good());
+        OFCHECK(asrc_item->setFilterMaterial("FILTER_MATERIAL").good());
+        OFCHECK(asrc_item->setFilterType("FILTER_TYPE").good());
+        OFCHECK(asrc_item->setFocalSpots(OFVector<Float64>(4, 4.4)).good());
+        OFCHECK(asrc_item->setKVP(5).good());
+        OFCHECK(asrc_item->setXRayTubeCurrentInmA(6).good());
+        asrc.getCTAdditionalXRaySourceItems().push_back(asrc_item);
+    }
+
+    FGTemporalPosition tempos;
+    OFCHECK(tempos.setTemporalPositionTimeOffset(1.0).good());
+
+    OFCHECK(ct->addForAllFrames(meas).good());
+    OFCHECK(ct->addForAllFrames(planpo).good());
+    OFCHECK(ct->addForAllFrames(planor).good());
+    OFCHECK(ct->addForAllFrames(ana).good());
+    OFCHECK(ct->addForAllFrames(voi).good());
+    OFCHECK(ct->addForAllFrames(irr).good());
+    OFCHECK(ct->addForAllFrames(itype).good());
+    OFCHECK(ct->addForAllFrames(atype).good());
+    OFCHECK(ct->addForAllFrames(adetails).good());
+    OFCHECK(ct->addForAllFrames(dyn).good());
+    OFCHECK(ct->addForAllFrames(pos).good());
+    OFCHECK(ct->addForAllFrames(geo).good());
+    OFCHECK(ct->addForAllFrames(rec).good());
+    OFCHECK(ct->addForAllFrames(exp).good());
+    OFCHECK(ct->addForAllFrames(det).good());
+    OFCHECK(ct->addForAllFrames(trans).good());
+    OFCHECK(ct->addForAllFrames(asrc).good());
+    OFCHECK(ct->addForAllFrames(tempos).good());
+}
+
+static void addFrames(EctEnhancedCT* ct)
+{
+    if (!ct)
+        return;
+
+    FGFrameContent* fg = new FGFrameContent();
+    fg->setStackID("1");
+    OFCHECK(fg);
+    if (fg)
+    {
+        EctEnhancedCT::FramesType frames = ct->getFrames();
+        for (Uint16 frameNo = 1; frameNo <= NUM_FRAMES; frameNo++)
+        {
+            OFCHECK(fg->setFrameAcquisitionNumber(frameNo).good());
+            OFCHECK(fg->setFrameReferenceDateTime("20190816092557").good());
+            OFCHECK(fg->setFrameAcquisitionDateTime("20190816092557").good());
+            OFCHECK(fg->setFrameAcquisitionDuration(0.001).good());
+            OFCHECK(fg->setInStackPositionNumber(frameNo).good());
+            OFCHECK(fg->setDimensionIndexValues(1, 0).good());
+            OFCHECK(fg->setDimensionIndexValues(frameNo, 1).good());
+            OFVector<FGBase*> groups;
+            groups.push_back(fg);
+
+            Uint16* data = new Uint16[NUM_PIXELS_PER_FRAME];
+            for (size_t i = 0; i < NUM_PIXELS_PER_FRAME; ++i)
+            {
+                data[i] = frameNo;
+            }
+            OFCHECK(
+                OFget<EctEnhancedCT::Frames<Uint16> >(&frames)->addFrame(data, NUM_PIXELS_PER_FRAME, groups).good());
+            delete[] data;
+        }
+    }
+    delete fg;
+}
+
+static void addDimensions(EctEnhancedCT* ct)
+{
+    if (!ct)
+        return;
+    IODMultiframeDimensionModule& dims = ct->getDimensions();
+    OFCHECK(dims.addDimensionIndex(
+                    DCM_StackID, "2.25.30855560781715986879861690673941231222", DCM_FrameContentSequence, "STACK_DIM")
+                .good());
+    OFCHECK(dims.addDimensionIndex(DCM_InStackPositionNumber,
+                                   "2.25.30855560781715986879861690673941231222",
+                                   DCM_FrameContentSequence,
+                                   "STACK_DIM")
+                .good());
+    OFunique_ptr<IODMultiframeDimensionModule::DimensionOrganizationItem> org(
+        new IODMultiframeDimensionModule::DimensionOrganizationItem);
+    if (org)
+    {
+        org->setDimensionOrganizationUID("2.25.30855560781715986879861690673941231222");
+        dims.getDimensionOrganizationSequence().push_back(org.release());
+    }
+}
+
+static OFString write(EctEnhancedCT* ct, DcmDataset& ds)
+{
+    OFCondition result = ct->writeDataset(ds);
+    OFCHECK(result.good());
+    if (result.bad())
+    {
+        OFLOG_ERROR(tRoundLogger, "Writing Enhanced CT dataset failed: " << result.text() << OFendl);
+    }
+    // Make dump and return it
+    OFStringStream sstream;
+    ds.print(sstream);
+    OFSTRINGSTREAM_GETOFSTRING(sstream, dump);
+    return dump;
+}
+
+static void writeAndCheckConcatenation(EctEnhancedCT* ct, OFList<OFFilename>& concats)
+{
+    ConcatenationCreator cc;
+    cc.setCfgFramesPerInstance(NUM_FRAMES_CONCAT);
+    OFCHECK(ct->writeConcatenation(cc).good());
+    size_t numInstances = cc.getNumInstances();
+    OFCHECK(numInstances == NUM_FRAMES);
+    OFCondition result;
+    for (size_t n = 0; n < numInstances; n++)
+    {
+        OFStringStream s;
+        s << "concat_" << n << "_";
+        OFTempFile tf(O_RDWR, "", s.str().c_str(), ".dcm");
+        result = cc.writeNextInstance(tf.getFilename());
+        OFCHECK(result.good());
+        if (result.good())
+        {
+            DcmFileFormat concat;
+            OFCHECK(concat.loadFile(tf.getFilename()).good());
+            checkConcatenationInstance(n, ct, concat.getDataset());
+            concats.push_back(tf.getFilename());
+            tf.stealFile();
+        }
+    }
+}
+
+static void checkConcatenationInstance(size_t numInstance, EctEnhancedCT* srcInstance, DcmDataset* concatInstance)
+{
+    EctEnhancedCT* concat = NULL;
+    OFCHECK(EctEnhancedCT::loadDataset(*concatInstance, concat).good());
+    if (concat)
+    {
+        size_t numFrames;
+        numFrames = concat->getNumberOfFrames();
+        OFCHECK(numFrames == 1);
+        IODMultiFrameFGModule::ConcatenationInfo& ci = concat->getConcatenationInfo();
+        OFString val;
+        OFCHECK(ci.getConcatenationUID(val).good());
+        OFCHECK(DcmUniqueIdentifier::checkStringValue(val, "1").good());
+        Uint32 frameOffsetNo = 0;
+        OFCHECK(ci.getConcatenationFrameOffsetNumber(frameOffsetNo).good());
+        OFCHECK(frameOffsetNo == numInstance);
+        Uint16 inConcatNo = 0;
+        OFCHECK(ci.getInConcatenationNumber(inConcatNo).good());
+        OFCHECK(inConcatNo == numInstance + 1);
+        Uint16 concatTotalNo = 0;
+        OFCHECK(ci.getInConcatenationTotalNumber(concatTotalNo).good());
+        OFCHECK(concatTotalNo == NUM_FRAMES);
+
+        OFString srcUID;
+        OFCHECK(ci.getSOPInstanceUIDOfConcatenationSource(srcUID).good());
+        OFCHECK(srcInstance->getSOPCommon().getSOPInstanceUID(val).good());
+        OFCHECK(srcUID == val);
+
+        OFCHECK(concat->getSOPCommon().getSOPInstanceUID(val).good());
+        OFCHECK(srcUID != val);
+
+        FunctionalGroups::const_iterator srcShared = srcInstance->getFunctionalGroups().getShared()->begin();
+        FunctionalGroups::const_iterator cShared   = concat->getFunctionalGroups().getShared()->begin();
+        size_t numShared                           = 0;
+        do
+        {
+            OFCHECK(srcShared->second->compare(*cShared->second) == 0);
+            srcShared++;
+            cShared++;
+            numShared++;
+        } while ((srcShared != srcInstance->getFunctionalGroups().getShared()->end())
+                 && (cShared != concat->getFunctionalGroups().getShared()->end()));
+        OFCHECK((srcShared == srcInstance->getFunctionalGroups().getShared()->end())
+                && (cShared == concat->getFunctionalGroups().getShared()->end()));
+        DcmSequenceOfItems* cPerFrame = NULL;
+        OFCHECK(concatInstance->findAndGetSequence(DCM_PerFrameFunctionalGroupsSequence, cPerFrame).good());
+
+        if (cPerFrame)
+        {
+            OFCHECK(cPerFrame->card() == 1);
+        }
+
+        OFBool perFrame = OFFalse;
+        FGBase* fg      = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTACQUISITIONDETAILS, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTACQUISITIONTYPE, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTADDITIONALXRAYSOURCE, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTEXPOSURE, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTGEOMETRY, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTIMAGEFRAMETYPE, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTPOSITION, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTRECONSTRUCTION, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTTABLEDYNAMICS, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTXRAYDETAILS, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_CTXRAYDETAILS, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_FRAMECONTENT, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFTrue);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_FRAMEANATOMY, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_FRAMEANATOMY, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_FRAMEVOILUTMETA, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_FRAMEANATOMY, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_IRRADIATIONEVENTIDENT, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_PIXELVALUETRANSMETA, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_IRRADIATIONEVENTIDENT, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = NULL;
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_PIXELMEASURES, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = NULL;
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_PLANEPOSPATIENT, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = NULL;
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_PLANEORIENTPATIENT, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_TEMPORALPOSITION, perFrame);
+        OFCHECK(fg != NULL);
+        OFCHECK(perFrame == OFFalse);
+
+        EctEnhancedCT::FramesType frames = concat->getFrames();
+        Uint16* frame                    = OFget<EctEnhancedCT::Frames<Uint16> >(&frames)->getFrame(0);
+        OFCHECK(frame != OFnullptr);
+        // Check that all pixels are set to their original source instances frame number (starting from 1)
+        for (size_t pix = 0; pix < NUM_PIXELS_PER_FRAME; pix++)
+        {
+            OFCHECK(frame[pix] == numInstance + 1);
+        }
+        delete concat;
+    }
+}
+
+void loadAndCheckConcatenation(const OFList<OFFilename>& concats)
+{
+    ConcatenationLoader cl;
+    OFCondition result = cl.scan(concats);
+    OFCHECK(result.good());
+    if (result.good())
+    {
+        DcmDataset merged;
+        EctEnhancedCT* mergedCT = NULL;
+        result                  = EctEnhancedCT::loadConcatenation(cl, cl.getInfo().begin()->first, mergedCT);
+        if (result.good())
+        {
+            OFStringStream s;
+            DcmDataset d;
+            result = mergedCT->writeDataset(d);
+            OFCHECK(result.good());
+            if (result.good())
+            {
+                // patch in old timestamp to match dump
+                OFCHECK(d.putAndInsertOFStringArray(DCM_ContentDate, "20190816").good());
+                OFCHECK(d.putAndInsertOFStringArray(DCM_ContentTime, "092557").good());
+                d.print(s);
+                checkCreatedObject(s.str().c_str());
+                delete mergedCT;
+            }
+        }
+    }
+}
+
+static void prepareExpectedDump()
+{
+    EXPECTED_DUMP += "\n";
+    EXPECTED_DUMP += "# Dicom-Data-Set\n";
+    EXPECTED_DUMP += "# Used TransferSyntax: Little Endian Explicit\n";
+    EXPECTED_DUMP += "(0008,0008) CS [ORIGINAL\\PRIMARY\\VOLUME\\MAXIMUM]        #  32, 4 ImageType\n";
+    EXPECTED_DUMP += "(0008,0016) UI =EnhancedCTImageStorage                  #  28, 1 SOPClassUID\n";
+    EXPECTED_DUMP
+        += "(0008,0018) UI [1.2.276.0.7230010.3.1.4.8323329.14863.1565940357.864813] #  56, 1 SOPInstanceUID\n";
+    EXPECTED_DUMP += "(0008,0020) DA [20190801]                               #   8, 1 StudyDate\n";
+    EXPECTED_DUMP += "(0008,0023) DA [20190816]                               #   8, 1 ContentDate\n";
+    EXPECTED_DUMP += "(0008,002a) DT [20190801120000]                         #  14, 1 AcquisitionDateTime\n";
+    EXPECTED_DUMP += "(0008,0030) TM [120000]                                 #   6, 1 StudyTime\n";
+    EXPECTED_DUMP += "(0008,0033) TM [092557]                                 #   6, 1 ContentTime\n";
+    EXPECTED_DUMP += "(0008,0050) SH (no value available)                     #   0, 0 AccessionNumber\n";
+    EXPECTED_DUMP += "(0008,0060) CS [CT]                                     #   2, 1 Modality\n";
+    EXPECTED_DUMP += "(0008,0070) LO [Open Connections]                       #  16, 1 Manufacturer\n";
+    EXPECTED_DUMP += "(0008,0090) PN (no value available)                     #   0, 0 ReferringPhysicianName\n";
+    EXPECTED_DUMP += "(0008,103e) LO [Test Description]                       #  16, 1 SeriesDescription\n";
+    EXPECTED_DUMP += "(0008,1090) LO [OC CT]                                  #   6, 1 ManufacturerModelName\n";
+    EXPECTED_DUMP += "(0008,9205) CS [MONOCHROME]                             #  10, 1 PixelPresentation\n";
+    EXPECTED_DUMP += "(0008,9206) CS [VOLUME]                                 #   6, 1 VolumetricProperties\n";
+    EXPECTED_DUMP
+        += "(0008,9207) CS [VOLUME_RENDER]                          #  14, 1 VolumeBasedCalculationTechnique\n";
+    EXPECTED_DUMP += "(0010,0010) PN [Bond^James]                             #  10, 1 PatientName\n";
+    EXPECTED_DUMP += "(0010,0020) LO [007]                                    #   4, 1 PatientID\n";
+    EXPECTED_DUMP += "(0010,0030) DA [19771007]                               #   8, 1 PatientBirthDate\n";
+    EXPECTED_DUMP += "(0010,0040) CS (no value available)                     #   0, 0 PatientSex\n";
+    EXPECTED_DUMP += "(0010,1010) AS [040Y]                                   #   4, 1 PatientAge\n";
+    EXPECTED_DUMP += "(0018,1000) LO [4711]                                   #   4, 1 DeviceSerialNumber\n";
+    EXPECTED_DUMP += "(0018,1020) LO [0.1]                                    #   4, 1 SoftwareVersions\n";
+    EXPECTED_DUMP += "(0018,5100) CS [HFS]                                    #   4, 1 PatientPosition\n";
+    EXPECTED_DUMP += "(0018,9004) CS [RESEARCH]                               #   8, 1 ContentQualification\n";
+    EXPECTED_DUMP += "(0018,9073) FD 2                                        #   8, 1 AcquisitionDuration\n";
+    EXPECTED_DUMP
+        += "(0020,000d) UI [1.2.276.0.7230010.3.1.2.8323329.14863.1565940357.864811] #  56, 1 StudyInstanceUID\n";
+    EXPECTED_DUMP
+        += "(0020,000e) UI [1.2.276.0.7230010.3.1.3.8323329.14863.1565940357.864812] #  56, 1 SeriesInstanceUID\n";
+    EXPECTED_DUMP += "(0020,0010) SH [1]                                      #   2, 1 StudyID\n";
+    EXPECTED_DUMP += "(0020,0011) IS [1]                                      #   2, 1 SeriesNumber\n";
+    EXPECTED_DUMP += "(0020,0013) IS [1]                                      #   2, 1 InstanceNumber\n";
+    EXPECTED_DUMP += "(0020,0052) UI [2.25.30853397773651184949181049330553108086] #  44, 1 FrameOfReferenceUID\n";
+    EXPECTED_DUMP += "(0020,1040) LO (no value available)                     #   0, 0 PositionReferenceIndicator\n";
+    EXPECTED_DUMP += "(0020,9221) SQ (Sequence with explicit length #=1)      #   0, 1 DimensionOrganizationSequence\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "    (0020,9164) UI [2.25.30855560781715986879861690673941231222] #  44, 1 DimensionOrganizationUID\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "(0020,9222) SQ (Sequence with explicit length #=2)      #   0, 1 DimensionIndexSequence\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=4)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "    (0020,9164) UI [2.25.30855560781715986879861690673941231222] #  44, 1 DimensionOrganizationUID\n";
+    EXPECTED_DUMP += "    (0020,9165) AT (0020,9056)                              #   4, 1 DimensionIndexPointer\n";
+    EXPECTED_DUMP += "    (0020,9167) AT (0020,9111)                              #   4, 1 FunctionalGroupPointer\n";
+    EXPECTED_DUMP += "    (0020,9421) LO [STACK_DIM]                              #  10, 1 DimensionDescriptionLabel\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=4)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "    (0020,9164) UI [2.25.30855560781715986879861690673941231222] #  44, 1 DimensionOrganizationUID\n";
+    EXPECTED_DUMP += "    (0020,9165) AT (0020,9057)                              #   4, 1 DimensionIndexPointer\n";
+    EXPECTED_DUMP += "    (0020,9167) AT (0020,9111)                              #   4, 1 FunctionalGroupPointer\n";
+    EXPECTED_DUMP += "    (0020,9421) LO [STACK_DIM]                              #  10, 1 DimensionDescriptionLabel\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "(0028,0002) US 1                                        #   2, 1 SamplesPerPixel\n";
+    EXPECTED_DUMP += "(0028,0004) CS [MONOCHROME2]                            #  12, 1 PhotometricInterpretation\n";
+    EXPECTED_DUMP += "(0028,0008) IS [2]                                      #   2, 1 NumberOfFrames\n";
+    EXPECTED_DUMP += "(0028,0010) US 2                                        #   2, 1 Rows\n";
+    EXPECTED_DUMP += "(0028,0011) US 2                                        #   2, 1 Columns\n";
+    EXPECTED_DUMP += "(0028,0100) US 16                                       #   2, 1 BitsAllocated\n";
+    EXPECTED_DUMP += "(0028,0101) US 16                                       #   2, 1 BitsStored\n";
+    EXPECTED_DUMP += "(0028,0102) US 15                                       #   2, 1 HighBit\n";
+    EXPECTED_DUMP += "(0028,0103) US 0                                        #   2, 1 PixelRepresentation\n";
+    EXPECTED_DUMP += "(0028,0301) CS [NO]                                     #   2, 1 BurnedInAnnotation\n";
+    EXPECTED_DUMP += "(0028,2110) CS [00]                                     #   2, 1 LossyImageCompression\n";
+    EXPECTED_DUMP += "(0040,0555) SQ (Sequence with explicit length #=0)      #   0, 1 AcquisitionContextSequence\n";
+    EXPECTED_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "(2050,0020) CS [IDENTITY]                               #   8, 1 PresentationLUTShape\n";
+    EXPECTED_DUMP
+        += "(5200,9229) SQ (Sequence with explicit length #=1)      #   0, 1 SharedFunctionalGroupsSequence\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=18)         #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0018,9301) SQ (Sequence with explicit length #=1)      #   0, 1 CTAcquisitionTypeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=4)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0018,9302) CS [CONSTANT_ANGLE]                         #  14, 1 AcquisitionType\n";
+    EXPECTED_DUMP += "        (0018,9303) FD 0.1                                      #   8, 1 TubeAngle\n";
+    EXPECTED_DUMP += "        (0018,9333) CS [YES]                                    #   4, 1 ConstantVolumeFlag\n";
+    EXPECTED_DUMP += "        (0018,9334) CS [NO]                                     #   2, 1 FluoroscopyFlag\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "    (0018,9304) SQ (Sequence with explicit length #=1)      #   0, 1 CTAcquisitionDetailsSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,0090) DS [20]                                     #   2, 1 DataCollectionDiameter\n";
+    EXPECTED_DUMP += "        (0018,1120) DS [5]                                      #   2, 1 GantryDetectorTilt\n";
+    EXPECTED_DUMP += "        (0018,1130) DS [50]                                     #   2, 1 TableHeight\n";
+    EXPECTED_DUMP += "        (0018,1140) CS [CW]                                     #   2, 1 RotationDirection\n";
+    EXPECTED_DUMP += "        (0018,9305) FD 5                                        #   8, 1 RevolutionTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9306) FD 1                                        #   8, 1 SingleCollimationWidth\n";
+    EXPECTED_DUMP += "        (0018,9307) FD 10                                       #   8, 1 TotalCollimationWidth\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0018,9308) SQ (Sequence with explicit length #=1)      #   0, 1 CTTableDynamicsSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0018,9309) FD 1                                        #   8, 1 TableSpeed\n";
+    EXPECTED_DUMP += "        (0018,9310) FD 0.1                                      #   8, 1 TableFeedPerRotation\n";
+    EXPECTED_DUMP += "        (0018,9311) FD 0.2                                      #   8, 1 SpiralPitchFactor\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0018,9312) SQ (Sequence with explicit length #=1)      #   0, 1 CTGeometrySequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=2)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,1110) DS [0.5]                                    #   4, 1 DistanceSourceToDetector\n";
+    EXPECTED_DUMP += "        (0018,9335) FD 5                                        #   8, 1 "
+                     "DistanceSourceToDataCollectionCenter\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0018,9314) SQ (Sequence with explicit length #=1)      #   0, 1 CTReconstructionSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,1100) DS [100]                                    #   4, 1 ReconstructionDiameter\n";
+    EXPECTED_DUMP += "        (0018,1210) SH [DUMMY]                                  #   6, 1 ConvolutionKernel\n";
+    EXPECTED_DUMP
+        += "        (0018,9315) CS [ALGO]                                   #   4, 1 ReconstructionAlgorithm\n";
+    EXPECTED_DUMP
+        += "        (0018,9316) CS [DUMMYGROUP]                             #  10, 1 ConvolutionKernelGroup\n";
+    EXPECTED_DUMP += "        (0018,9319) FD 90                                       #   8, 1 ReconstructionAngle\n";
+    EXPECTED_DUMP += "        (0018,9320) SH [FILTER]                                 #   6, 1 ImageFilter\n";
+    EXPECTED_DUMP
+        += "        (0018,9322) FD 0.1\\0.1                                  #  16, 2 ReconstructionPixelSpacing\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0018,9321) SQ (Sequence with explicit length #=1)      #   0, 1 CTExposureSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=10)         #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0018,115e) DS [0.5]                                    #   4, 1 "
+                     "ImageAndFluoroscopyAreaDoseProduct\n";
+    EXPECTED_DUMP
+        += "        (0018,1271) FD 0.6                                      #   8, 1 WaterEquivalentDiameter\n";
+    EXPECTED_DUMP += "        (0018,1272) SQ (Sequence with explicit length #=1)      #   0, 1 "
+                     "WaterEquivalentDiameterCalculationMethodCodeSequence\n";
+    EXPECTED_DUMP += "          (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "            (0008,0100) SH [113987]                                 #   6, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "            (0008,0102) SH [DCM]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "            (0008,0104) LO [AAPM 220]                               #   8, 1 CodeMeaning\n";
+    EXPECTED_DUMP
+        += "          (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP
+        += "        (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "        (0018,9323) CS [WEIRD]                                  #   6, 1 ExposureModulationType\n";
+    EXPECTED_DUMP += "        (0018,9324) FD 0.2                                      #   8, 1 EstimatedDoseSaving\n";
+    EXPECTED_DUMP += "        (0018,9328) FD 0.4                                      #   8, 1 ExposureTimeInms\n";
+    EXPECTED_DUMP += "        (0018,9330) FD 0.7                                      #   8, 1 XRayTubeCurrentInmA\n";
+    EXPECTED_DUMP += "        (0018,9332) FD 0.3                                      #   8, 1 ExposureInmAs\n";
+    EXPECTED_DUMP += "        (0018,9345) FD 0.1                                      #   8, 1 CTDIvol\n";
+    EXPECTED_DUMP
+        += "        (0018,9346) SQ (Sequence with explicit length #=1)      #   0, 1 CTDIPhantomTypeCodeSequence\n";
+    EXPECTED_DUMP += "          (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "            (0008,0100) SH [113682]                                 #   6, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "            (0008,0102) SH [DCM]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "            (0008,0104) LO [ACR Accreditation Phantom - CT]         #  30, 1 CodeMeaning\n";
+    EXPECTED_DUMP
+        += "          (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP
+        += "        (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0018,9325) SQ (Sequence with explicit length #=1)      #   0, 1 CTXRayDetailsSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0018,0060) DS [5]                                      #   2, 1 KVP\n";
+    EXPECTED_DUMP += "        (0018,1160) SH [FILTER_TYPE]                            #  12, 1 FilterType\n";
+    EXPECTED_DUMP += "        (0018,1190) DS [4.4\\4.4\\4.4\\4.4]                        #  16, 4 FocalSpots\n";
+    EXPECTED_DUMP += "        (0018,7050) CS [FILTER_MATERIAL]                        #  16, 1 FilterMaterial\n";
+    EXPECTED_DUMP
+        += "        (0018,9351) FL 2                                        #   4, 1 CalciumScoringMassFactorPatient\n";
+    EXPECTED_DUMP += "        (0018,9352) FL 1\\1\\1                                    #  12, 3 "
+                     "CalciumScoringMassFactorDevice\n";
+    EXPECTED_DUMP += "        (0018,9353) FL 3                                        #   4, 1 EnergyWeightingFactor\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0018,9326) SQ (Sequence with explicit length #=1)      #   0, 1 CTPositionSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,9313) FD 2\\2\\2                                    #  24, 3 DataCollectionCenterPatient\n";
+    EXPECTED_DUMP += "        (0018,9318) FD 1\\1\\1                                    #  24, 3 "
+                     "ReconstructionTargetCenterPatient\n";
+    EXPECTED_DUMP += "        (0018,9327) FD 100                                      #   8, 1 TablePosition\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0018,9329) SQ (Sequence with explicit length #=1)      #   0, 1 CTImageFrameTypeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=4)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,9007) CS [ORIGINAL\\PRIMARY\\VOLUME\\MAXIMUM]        #  32, 4 FrameType\n";
+    EXPECTED_DUMP += "        (0008,9205) CS [MONOCHROME]                             #  10, 1 PixelPresentation\n";
+    EXPECTED_DUMP += "        (0008,9206) CS [VOLUME]                                 #   6, 1 VolumetricProperties\n";
+    EXPECTED_DUMP
+        += "        (0008,9207) CS [VOLUME_RENDER]                          #  14, 1 VolumeBasedCalculationTechnique\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "    (0018,9360) SQ (Sequence with explicit length #=1)      #   0, 1 CTAdditionalXRaySourceSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=8)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0018,0060) DS [5]                                      #   2, 1 KVP\n";
+    EXPECTED_DUMP
+        += "        (0018,0090) DS [1]                                      #   2, 1 DataCollectionDiameter\n";
+    EXPECTED_DUMP += "        (0018,1160) SH [FILTER_TYPE]                            #  12, 1 FilterType\n";
+    EXPECTED_DUMP += "        (0018,1190) DS [4.4\\4.4\\4.4\\4.4]                        #  16, 4 FocalSpots\n";
+    EXPECTED_DUMP += "        (0018,7050) CS [FILTER_MATERIAL]                        #  16, 1 FilterMaterial\n";
+    EXPECTED_DUMP += "        (0018,9330) FD 6                                        #   8, 1 XRayTubeCurrentInmA\n";
+    EXPECTED_DUMP += "        (0018,9332) FD 3                                        #   8, 1 ExposureInmAs\n";
+    EXPECTED_DUMP += "        (0018,9353) FL 2                                        #   4, 1 EnergyWeightingFactor\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0018,9477) SQ (Sequence with explicit length #=1)      #   0, 1 "
+                     "IrradiationEventIdentificationSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0008,3010) UI [2.25.30853892236613436472911970638347155062] #  44, 1 IrradiationEventUID\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0020,9071) SQ (Sequence with explicit length #=1)      #   0, 1 FrameAnatomySequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=2)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0008,2218) SQ (Sequence with explicit length #=1)      #   0, 1 AnatomicRegionSequence\n";
+    EXPECTED_DUMP += "          (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "            (0008,0100) SH [12738006]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "            (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "            (0008,0104) LO [Brain]                                  #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP
+        += "          (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP
+        += "        (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "        (0020,9072) CS [B]                                      #   2, 1 FrameLaterality\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0020,9113) SQ (Sequence with explicit length #=1)      #   0, 1 PlanePositionSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0020,0032) DS [0.0\\0.0\\0.0]                            #  12, 3 ImagePositionPatient\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0020,9116) SQ (Sequence with explicit length #=1)      #   0, 1 PlaneOrientationSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0020,0037) DS [1.0\\0.0\\0.0\\0.0\\1.0\\0.0]                #  24, 6 ImageOrientationPatient\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0020,9310) SQ (Sequence with explicit length #=1)      #   0, 1 TemporalPositionSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0020,930d) FD 1                                        #   8, 1 TemporalPositionTimeOffset\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0028,9110) SQ (Sequence with explicit length #=1)      #   0, 1 PixelMeasuresSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0018,0050) DS [1.0]                                    #   4, 1 SliceThickness\n";
+    EXPECTED_DUMP += "        (0018,0088) DS [0.05]                                   #   4, 1 SpacingBetweenSlices\n";
+    EXPECTED_DUMP += "        (0028,0030) DS [0.1\\0.1]                                #   8, 2 PixelSpacing\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0028,9132) SQ (Sequence with explicit length #=1)      #   0, 1 FrameVOILUTSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0028,1050) DS [1000]                                   #   4, 1 WindowCenter\n";
+    EXPECTED_DUMP += "        (0028,1051) DS [2000]                                   #   4, 1 WindowWidth\n";
+    EXPECTED_DUMP
+        += "        (0028,1055) LO [BRAIN]                                  #   6, 1 WindowCenterWidthExplanation\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "    (0028,9145) SQ (Sequence with explicit length #=1)      #   0, 1 PixelValueTransformationSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0028,1052) DS [0]                                      #   2, 1 RescaleIntercept\n";
+    EXPECTED_DUMP += "        (0028,1053) DS [1]                                      #   2, 1 RescaleSlope\n";
+    EXPECTED_DUMP += "        (0028,1054) LO [HU]                                     #   2, 1 RescaleType\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "(5200,9230) SQ (Sequence with explicit length #=2)      #   0, 1 PerFrameFunctionalGroupsSequence\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0020,9111) SQ (Sequence with explicit length #=1)      #   0, 1 FrameContentSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,9074) DT [20190816092557]                         #  14, 1 FrameAcquisitionDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9151) DT [20190816092557]                         #  14, 1 FrameReferenceDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9220) FD 0.001                                    #   8, 1 FrameAcquisitionDuration\n";
+    EXPECTED_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    EXPECTED_DUMP += "        (0020,9057) UL 1                                        #   4, 1 InStackPositionNumber\n";
+    EXPECTED_DUMP
+        += "        (0020,9156) US 1                                        #   2, 1 FrameAcquisitionNumber\n";
+    EXPECTED_DUMP += "        (0020,9157) UL 1\\1                                      #   8, 2 DimensionIndexValues\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0020,9111) SQ (Sequence with explicit length #=1)      #   0, 1 FrameContentSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,9074) DT [20190816092557]                         #  14, 1 FrameAcquisitionDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9151) DT [20190816092557]                         #  14, 1 FrameReferenceDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9220) FD 0.001                                    #   8, 1 FrameAcquisitionDuration\n";
+    EXPECTED_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    EXPECTED_DUMP += "        (0020,9057) UL 2                                        #   4, 1 InStackPositionNumber\n";
+    EXPECTED_DUMP
+        += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    EXPECTED_DUMP += "        (0020,9157) UL 1\\2                                      #   8, 2 DimensionIndexValues\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "(7fe0,0010) OW 0001\\0001\\0001\\0001\\0002\\0002\\0002\\0002  #  16, 1 PixelData\n";
+}
+
+static void checkCreatedObject(const OFString& ds_dump)
+{
+    OFBool dump_ok = (ds_dump == EXPECTED_DUMP);
+    OFCHECK(dump_ok);
+    if (!dump_ok)
+    {
+        CERR << "Dump produced: " << OFendl << ds_dump << OFendl;
+        CERR << "------------------------------------" << OFendl;
+        CERR << "Dump expected: " << OFendl << EXPECTED_DUMP << OFendl;
+        CERR << "------------------------------------" << OFendl;
+    }
+}
diff --git a/dcmect/tests/tests.cc b/dcmect/tests/tests.cc
new file mode 100644 (file)
index 0000000..54a6ca0
--- /dev/null
@@ -0,0 +1,27 @@
+/*
+ *
+ *  Copyright (C) 2019, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmect
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Main test program for dcmect
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+#include "dcmtk/ofstd/oftest.h"
+
+OFTEST_REGISTER(dcmect_huge_concat);
+OFTEST_REGISTER(dcmect_roundtrip);
+OFTEST_MAIN("dcmect")
diff --git a/dcmfg/include/dcmtk/dcmfg/concatenationcreator.h b/dcmfg/include/dcmtk/dcmfg/concatenationcreator.h
new file mode 100644 (file)
index 0000000..c97ad29
--- /dev/null
@@ -0,0 +1,265 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for creating Concatenations
+ *
+ */
+
+#ifndef CONCATENATIONCREATOR_H
+#define CONCATENATIONCREATOR_H
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dctk.h"
+#include "dcmtk/dcmfg/fgdefine.h"
+
+/** Class for creating Concatenations from existing SOP Instances.
+ *  As input, a user can either provide a full SOP Instance with Pixel Data
+ *  attribute, or a SOP Instance plus separate pixel data as a vector of frame data.
+ *  The input file is uncompressed if necessary and possible, and the resulting
+ *  concatenation instances will also contain uncompressed pixel data.
+ *  During conversion, the original source pixel data is held into memory and
+ *  additionally one of the concatenation instances the moment it is being produced
+ *  when calling writeNextInstance() (see below).
+ *  The following workflow must be used to create a Concatenation:
+ *  <ul>
+ *  <li>Call to one of the setCfgInput() methods in order to set the concatenation
+ *  source data, i.e. the SOP Instance that should be split into a number of
+ *  concatenation instances.</li>
+ *  <li>Call to other setCfg...() calls in order to set conversion options. For example
+ *  the number of frames per concatenation instance produced can be configured by calling
+ *  setCfgFramesPerInstance(). Per default, 25 frames per instance are being used.</li>
+ *  <li>Call to one of the writeNextInstance() methods in order to write the next
+ *  concatenation instance.</li>
+ *  <li>Call to the load() method in order to load of the the Concatenations found
+ *  during scan(). Selection is done via the Concatenations Concatenation UID.
+ *  The result is made available as a single, merged dataset without Pixel Data attribute
+ *  and a vector containing all frames of the merged instance.</li>
+ * </ul>
+ */
+class DCMTK_DCMFG_EXPORT ConcatenationCreator
+{
+
+public:
+    /** Constructor
+     */
+    ConcatenationCreator();
+
+    /** Virtual destructor
+     */
+    virtual ~ConcatenationCreator();
+
+    /** Set input dataset that should be split into a number of
+     *  concatenation instances
+     *  @param  srcDataset The dataset to read from (must not be NULL)
+     *  @param  transferOwnership If OFTrue, the ConcatenationCreator class will
+     *          free memory of the srcDataset after processing.
+     *  @return EC_Normal if input is considered valid (up to now), error otherwise
+     */
+    virtual OFCondition setCfgInput(DcmItem* srcDataset, OFBool transferOwnership);
+
+    /** Set input dataset with separate pixel data that should be split
+     *  into a number of concatenation instances.
+     *  @param  srcDataset The dataset to read from (must not be NULL and not contain
+     *          the Pixel Data attribute (on main level)
+     *  @param  pixelData Raw buffer of source pixel data
+     *  @param  pixelDataLength Length of pixelData buffer in bytes
+     *  @param  transferOwnership If OFTrue, the ConcatenationCreator class will
+     *          free memory of the srcDataset and pixelData after processing.
+     *  @return EC_Normal if input is considered valid (up to now), error otherwise
+     */
+    virtual OFCondition
+    setCfgInput(DcmItem* srcDataset, Uint8* pixelData, size_t pixelDataLength, OFBool transferOwnership);
+
+    /** Set number of frames that should go into a single concatenation instance produced.
+     *  The last concatenation instance might have less frames. This setting also
+     *  directly determines the number of instances produced for a specific input.
+     *  @param numFramesPerInstance The number of frames to be used for each instance
+     *         (last instance may differ)
+     *  @return EC_Normal if setting is ok, error otherwise
+     */
+    virtual OFCondition setCfgFramesPerInstance(Uint32 numFramesPerInstance);
+
+    /** Set the Instance Number that should be used in the concatenation instances produced.
+     *  @param  instanceNumber The Instance Number to be used
+     *  @return OFTrue if Instance Number is acceptable, OFFalse otherwise
+     */
+    virtual OFBool setCfgInstanceNumber(const OFString& instanceNumber);
+
+    /** Write first/next concatenation instance
+     *  @param  dstDataset The dataset to write to
+     *  @return EC_Normal if instance could be written,
+     *  FG_EC_ConcatenationComplete error code if the last instance has already been written,
+     *  other error otherwise.
+     */
+    virtual OFCondition writeNextInstance(DcmItem& dstDataset);
+
+    /** Write first/next concatenation instance to given filename
+     *  @param  fn The filename to write to
+     *  @return EC_Normal if instance could be written,
+     *  FG_EC_ConcatenationComplete error code if the last instance has already been written,
+     *  other error otherwise.
+     */
+    virtual OFCondition writeNextInstance(const OFFilename& fn);
+
+    /** Get number of concatenation instances that will be produced.
+     *  This can only be used after setCfgInput() was successful; otherwise
+     *  it will always return 0.
+     *  @return The number of instances that will be produced
+     */
+    virtual size_t getNumInstances();
+
+protected:
+    /** Check whether SOP Class of given dataset does allow Concatenation.
+     *  Right now the Standard forbids Concatenations for:
+     *  <ul>
+     *  <li>Ophthalmic Tomography Image Storage</li>
+     *  <li>Ophthalmic Optical Coherence Tomography B-scan Volume Analysis Storage</li>
+     *  </ul>
+     *  @param  srcDataset The dataset to check SOP Class for
+     *  @return OFTrue if Concatenation is permitted, OFFalse otherwise
+     */
+    virtual OFBool checkSOPClass(DcmItem& srcDataset);
+
+    /** Check whether color model (Photometric Interpretation) and planar configuration
+     *  are acceptable.
+     *  Right now this class supports the following color models:
+     *  <ul>
+     *  <li>RGB</li>
+     *  <li>YBR_FULL</li>
+     *  <li>MONOCHROME1</li>
+     *  <li>MONOCHROME2</li>
+     *  </ul>
+     *  Also, only Planar Configuration=0 is supported (or empty value implicating
+     *  the same plane configuration).
+     *  @param  srcDataset The dataset to check
+     *  @return OFTrue if color model and planar configuration is permitted, OFFalse otherwise
+     */
+    virtual OFBool checkColorModel(DcmItem& srcDataset);
+
+    /** Insert Concatenation attributes into destination dataset.
+     *  @param  dstDataset The destination dataset to write to
+     *  @param  numFramesCurrentInstance The number of frames that will go into
+     *          the dataset
+     *  @return EC_Normal if setting worked, error otherwise
+     */
+    virtual OFCondition setConcatenationAttributes(DcmItem& dstDataset, Uint32 numFramesCurrentInstance);
+
+    /** Advance internal counters to next frame
+     *  @return EC_Normal if there is a next frame, error otherwise
+     */
+    virtual OFCondition goToNextFrame();
+
+    /** Return number of frames that must be written into current instance.
+     *  Will be the same for each instance except (potentially) the last one.
+     *  @return Number of frames
+     */
+    virtual Uint32 numFramesCurrentDstInstance();
+
+    /** Configure class based on input/configuration settings, i.e. prepare for
+     *  concatenation writing.
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition configureCommon();
+
+private:
+
+    /// Maximum number of instances that make up a Concatenation (=2^16-1=65535),
+    /// derived from attributes In-concatentation Number and In-concatenation Total Number
+    /// that only store 16 bit values (VR US).
+    static Uint16 const m_MAX_INSTANCES_PER_CONCATENATION;
+
+    /// Maximum number of bytes for uncompressed pixel data (=2^32-2), derived from
+    /// 32 bit length field of Pixel Data attribute with even length being required.
+    static Uint32 const m_MAX_PIXEL_DATA_LENGTH;
+
+    /// Flag denoting whether class is configured (i.e. configureCommon() has been called)
+    /// and ready for concatenation writing.
+    OFBool m_configured;
+
+    /// Flag denoting whether source data (dataset and/with frame data) should be
+    /// deleted by this class (OFTrue) or not (OFFalse). Value is initially OFFalse
+    /// but a value must be provided in any case in setCfgInput().
+    OFBool m_cfgTransferOwnership;
+
+    /// Number of instances each concatenation instance should contain (last may differ)
+    /// as configured by the user using setCfgFramesPerInstance(). Default is 25.
+    Uint32 m_cfgNumFramesPerInstance;
+
+    /// Number of bytes used for each frame (same in source instance and concatenation instances).
+    /// Default is 25. Can be set by setCfgFramesPerInstance().
+    size_t m_numBytesFrame;
+
+    /// Pointer to source dataset; will be modified during conversion (but content is restored
+    /// before the call to this class returns).
+    /// Once the ConcatenationCreator creator class goes out of scope or reset() is being called,
+    /// it is set to NULL. If m_cfgTransferOwnership is OFTrue, memory is freed by this class, too.
+    DcmItem* m_srcDataset;
+
+    /// SOP Instance UID of source instance provided in setCfgInput()
+    OFString m_srcSOPInstanceUID;
+
+    /// Pointer to source pixel data; will be modified during conversion (but content is restored
+    /// before the call to this class returns).
+    /// Once the ConcatenationCreator creator class goes out of scope or reset() is being called,
+    /// it is set to NULL. If m_cfgTransferOwnership is OFTrue, memory is freed by this class, too.
+    Uint8* m_srcPixelData;
+
+    /// VR of pixel data extracted/derived from source dataset. EVR_OB and EVR_OW are supported.
+    /// Initially set to EVR_Unknown.
+    DcmEVR m_VRPixelData;
+
+    /// Pointer to Per-Frame Functional Group Sequence of source dataset. Use to copy
+    /// per-frame items to concatenation instances as needed.
+    DcmSequenceOfItems* m_srcPerFrameFG;
+
+    /// Number of frames in source instance.
+    Uint32 m_srcNumFrames;
+
+    /// Number of instances to be produced for Concatenation.
+    /// This is limited to 16 bit since the attributes
+    /// In-concatentation Number and In-concatenation Total Number only
+    /// stores 16 bit values (VR US).
+    Uint16 m_dstNumInstances;
+
+    /// Number of Frames per instance (cached) to be produced for
+    /// all frames (last frame may differ)
+    Uint32 m_dstNumFramesPerInstance;
+
+    /// Number of Frames per instance (cached) to be produced for
+    /// last frame
+    Uint32 m_dstNumFramesLastInstance;
+
+    /// Concatenation UID to be used in the concatenation instances. Automatically
+    /// created during conversion.
+    OFString m_dstConcatenationUID;
+
+    /// Instance Number to be used in concatenation instances produced. Can be
+    /// configured using setCfgInstanceNumber().
+    OFString m_dstInstanceNumber;
+
+    /// Source frame that is used next in conversion
+    Uint16 m_currentSrcFrame;
+
+    /// Per frame FG item that is used next in conversion
+    DcmItem* m_currentPerFrameItem;
+
+    /// Next instance number that is about to be produced
+    Uint16 m_currentInstanceNum;
+};
+
+#endif // CONCATENATIONCREATOR_H
diff --git a/dcmfg/include/dcmtk/dcmfg/concatenationloader.h b/dcmfg/include/dcmtk/dcmfg/concatenationloader.h
new file mode 100644 (file)
index 0000000..1ba53cd
--- /dev/null
@@ -0,0 +1,369 @@
+/*
+ *
+ *  Copyright (C) 2019-2020, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for loading Concatenations
+ *
+ */
+
+#ifndef CONCATENATIONLOADER_H
+#define CONCATENATIONLOADER_H
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmfg/fgdefine.h"
+#include "dcmtk/dcmiod/iodtypes.h"
+#include "dcmtk/dcmiod/iodutil.h"
+#include "dcmtk/ofstd/oflist.h"
+#include "dcmtk/ofstd/ofmap.h"
+
+class DcmDataset;
+
+/** Class for scanning files for concatenations and if desired, load
+ *  one of them. If successful, loading produces the merged SOP Instance
+ *  as a single dataset plus its frames in a separate data structure. The following
+ *  workflow must be used:
+ *  <ul>
+ *  <li>Call to one of the scan() methods.</li>
+ *  <li>If scanning was successful, call getInfo() to get information about the
+ *  concatenations found by scan(). getFailedFiles() will return those files
+ *  who could not be read, do not provide Concatenation information or had other errors.</li>
+ *  <li>Call to the load() method in order to load of the the Concatenations found
+ *  during scan(). Selection is done via the Concatenations Concatenation UID.
+ *  The result is made available as a single, merged dataset without Pixel Data attribute
+ *  and a vector containing all frames of the merged instance.</li>
+ * </ul>
+ */
+class DCMTK_DCMFG_EXPORT ConcatenationLoader
+{
+
+public:
+    /// Structure representing information about a Concatenation,
+    /// consisting of its instances and common data.
+    struct DCMTK_DCMFG_EXPORT Info
+    {
+        /// Struct representing single SOP Instance being part of a Concatenation.
+        struct DCMTK_DCMFG_EXPORT Instance
+        {
+            /// Filename of concatenation instance
+            OFFilename m_Filename;
+            /// SOP Instance UID of concatenation instance
+            OFString m_sopInstanceUID;
+            /// Number of Frames extracted from concatenation instance
+            Uint32 m_NumberOfFrames;
+            /// In-Concatenation Number extracted from concatenation instance
+            Uint16 m_InConcatenationNumber;
+
+            /** Virtual destructor, frees memory
+             */
+            virtual ~Instance();
+
+            /** Default constructor
+             */
+            Instance();
+        };
+
+        /** Default constructor */
+        Info();
+
+        /** Copy constructor
+         *  @param  rhs The Info to copy from
+         */
+        Info(const Info& rhs);
+
+        /** Assignment operator
+         *  @param  rhs The Info to copy from
+         *  @return Reference to "this" object
+         */
+        Info& operator=(const Info& rhs);
+
+        /// List of instances that belong to this Concatenation
+        OFList<Instance> m_Files;
+
+        /// File that contains the source of this Concatenation, i.e.
+        /// the SOP Instance UID of Concatenation Source tag points to.
+        /// Might be empty if such file is not found during scanning.
+        OFFilename m_FileConatenationSource;
+
+        /// Concatenation UID of this Concatenation, extracted from concatenation instances
+        OFString m_ConcatenationUID;
+
+        /// SOP Instance UID of Concatenation Source, extracted from concatenation instances
+        OFString m_SourceUID;
+
+        /// In-Concatenation Total Number, extracted from concatenation instances (optional in DICOM)
+        Uint16 m_inConcatTotalNumber;
+
+        /// Total number of frames, i.e. the number of frames that make up this concatenation instance.
+        /// The number is computed by summing up the number of frames in instances found during scanning.
+        size_t m_NumTotalFrames;
+
+        /// Patient ID extracted from concatenation instances
+        OFString m_PatientID;
+
+        /// Study Instance UID extracted from concatenation instances
+        OFString m_StudyInstanceUID;
+
+        /// Series Instance UID extracted from concatenation instances
+        OFString m_SeriesInstanceUID;
+
+        /// SOP Class UID extracted from concatenation instances
+        OFString m_SOPClassUID;
+
+        /// Bits Allocated extracted from concatenation instances
+        Uint16 m_BitsAlloc;
+
+        /// Rows extracted from concatenation instances
+        Uint16 m_Rows;
+
+        /// Columns extracted from concatenation instances
+        Uint16 m_Cols;
+
+        /** Print overview of this Concatenation
+         *  @param  out The stream to print to
+         */
+        void print(OFStringStream& out);
+
+        /** Virtual destructor
+         */
+        virtual ~Info();
+    };
+
+    /// structure representing error information about a failed file
+    struct DCMTK_DCMFG_EXPORT Failure
+    {
+      /// filename
+      OFFilename fname;
+
+      /// error text
+      OFString errorText;
+
+      /// SOP Instance UID
+      OFString sopInstance;
+
+      /** constructor.
+       *  @param fn filename
+       *  @param err error text
+       *  @param uid SOP instance UID
+       */
+      Failure(const OFFilename& fn, const OFString& err, const OFString& uid)
+      : fname(fn), errorText(err), sopInstance(uid) {}
+    };
+
+    /// Result type of scan()
+    typedef OFMap<OFString, ConcatenationLoader::Info*> TScanResult;
+
+    /// Iterator type for iterating over scan() results
+    typedef OFMap<OFString, ConcatenationLoader::Info*>::iterator ScanResultIt;
+
+    /// Result type for the failures reported by scan()
+    typedef OFList<Failure> TScanFailures;
+
+    /// Result type for iterating the failures reported by scan()
+    typedef OFListIterator(Failure) TScanFailureIt;
+
+    /** Constructor
+     */
+    ConcatenationLoader();
+
+    /** Virtual destructor
+     */
+    virtual ~ConcatenationLoader();
+
+    /** Ignore missing SOP Instance UID of Concatenation Source
+     *  @param  ignore If OFTrue,  missing or empty SOP Instance UID of Concatenation Source tag is
+     *          ignored and operation continues.
+     */
+    virtual void setIgnoreMissingSourceUID(const OFBool ignore);
+
+    /** Scan given list of files for Concatenations. If successful, a results
+     *  can be accessed by calling getInfo() which contains an overview of the
+     *  Concatenations found (and files that failed during reading).
+     *  @param  files The files to scan
+     *  @return EC_Normal if scanning was successful, i.e. at least one Concatenation
+     *          could be discovered successfully.
+     */
+    virtual OFCondition scan(const OFList<OFFilename>& files);
+
+    /** Scan given directory for Concatenations. If successful, a results
+     *  can be accessed by calling getInfo() which contains an overview of the
+     *  Concatenations found (and files that failed during reading).
+     *  @param  directory The directory to scan
+     *  @param  pattern The search pattern (* per default)
+     *  @param  recursive If OFTrue, sub directories are scanned, too (default: OFTrue)
+     *  @return EC_Normal if scanning was successful, i.e. at least one Concatenation
+     *          could be discovered successfully.
+     */
+    virtual OFCondition scan(const OFFilename& directory, const OFFilename& pattern = "*", OFBool recursive = OFTrue);
+
+    /** Get successful results of scan() operation. Returns empty result set is scan() has
+     *  not been called before.
+     *  @return The results of the scan() operation
+     */
+    virtual const TScanResult& getInfo();
+
+    /** Get failed files of scan() operation. Returns empty result set is scan() has
+     *  not been called before (may be empty otherwise).
+     *  @return The failed files of the scan() operation
+     */
+    virtual const TScanFailures& getFailedFiles();
+
+    /** Load Concatenation and merge it into "original" source dataset.
+     *  The Concatenation to be loaded is selected by its Concatenation UID.
+     *  Frames are not written to the dataset's Pixel Data attribute but instead
+     *  reside in a frame structure provided by the caller (since they could exceed
+     *  the uncompressed maximum of 4 GB allowed in a single dataset).
+     *  @param  concatenationUID The Concatenation UID of the Concatenation
+     *          to be loaded
+     *  @param  dataset The result dataset. The caller must hand in a pointer to
+     *          a valid dataset, i.e. memory allocation must be done by the caller.
+     *          During loading, the dataset must not be freed outside this class.
+     *          However, the caller stays responsible to delete the dataset after usage.
+     *  @param  frames The resulting frames. Vector should provided empty by the user.
+     *          The user is responsible for deleting frames after successful operation.
+     *          If load() fails, this parameter should return an empty vector.
+     *  @return EC_Normal if loading Concatenation worked, error otherwise.
+     */
+    virtual OFCondition
+    load(const OFString& concatenationUID, DcmDataset* dataset, OFVector<DcmIODTypes::Frame*>& frames);
+
+protected:
+    /** Handles single file of a Concatenation and extracts structure for later
+     *  access by the user.
+     *  @param  file The file to process
+     *  @param  info The concatenation information structure to store results to
+     */
+    virtual void handleFile(const OFFilename& file, ConcatenationLoader::Info& info);
+
+    /** Checks an current file's information whether it fits to the rest of the
+     *  Concatenation instances already read. If this is the case, the instance's
+     *  information is added to the results.
+     *  @param  info Information for this Concatenation
+     *  @param  inst Instance information that should be added to the Concatenation
+     *  @param  error Error, if instance cannot be processed/added, otherwise empty.
+     */
+    virtual void checkAndInsertInfo(const ConcatenationLoader::Info& info,
+                                    const ConcatenationLoader::Info::Instance& inst,
+                                    OFString& error);
+
+    /** Check whether two numbers equal to 0 or empty.
+     *  @param  num1 The first number
+     *  @param  num2 The second number
+     *  @return OFTrue if both number are equal or one of them is 0, OFFalse otherwise.
+     */
+    virtual OFBool zeroOrEqual(const size_t num1, const size_t num2);
+
+    /** Check whether two strings are equal or one of them is empty.
+     *  @param  str1 The first string
+     *  @param  str2 The second string
+     *  @return OFTrue if both strings are equal or one of them is empty, OFFalse otherwise.
+     */
+    virtual OFBool emptyOrEqual(const OFString& str1, const OFString& str2);
+
+    /** Get that number from both which is not 0.
+     *  @param  num1 The first number
+     *  @param  num2 The second number
+     *  @return num1 if num 1 is not zero, num 2 otherwise.
+     */
+    template <typename T>
+    T getNotZero(const T num1, const T num2);
+
+    /** Perform consistency checks on the Concatenations found.
+     *  @return EC_Normal if successful, failure otherwise
+     */
+    virtual OFCondition doScanFinalChecks();
+
+    /** Prepare template (dataset) that is used to represent the final
+     *  result dataset.
+     *  @param  firstInstance The first (or any instance) of the concatenation
+     *          instances that will be used to create the result dataset.
+     *  @return EC_Normal if successful, failure otherwise
+     */
+    virtual OFCondition prepareTemplate(Info& firstInstance);
+
+    /** Extract frames from given item. Works for Bits Allocated = 8
+     *  and Bits Allocated = 16. Resulting frames are stored
+     *  in member variable.
+     *  @param  item The item to read Pixel Data attribute from
+     *  @param  info Concatenation information providing pixel meta data
+     *          like Rows and Columns
+     *  @param  numFrames The number of frames to extract from item's
+     *          Pixel Data attribute
+     *  @return EC_Normal if extraction was successful, error otherwise.
+     */
+    virtual OFCondition extractFrames(DcmItem& item, Info& info, Uint32 numFrames);
+
+    /** Extract binary frames (Bits Allocated = 1) from given item.
+     *  The resulting frames are stored in member variable.
+     *  @param  item The item to read Pixel Data attribute from
+     *  @param  info Concatenation information providing pixel meta data
+     *          like Rows and Columns
+     *  @param  numFrames The number of frames to extract from item's
+     *          Pixel Data attribute
+     *  @return EC_Normal if extraction was successful, error otherwise.
+     */
+    virtual OFCondition extractBinaryFrames(DcmItem& item, Info& info, Uint32 numFrames);
+
+    /** Deletes those concatenation attributes from given item that are not
+     *  used or get a different value in the resulting merged dataset.
+     *  @param  item The item to delete from
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition deleteConcatAttributes(DcmItem& item);
+
+    /** Moves all Per-Frame Functional Group items found in given item
+     *  to result instance.
+     *  @param  item The item to delete from
+     *  @return EC_Normal if deletion was successful, error otherwise
+     */
+    virtual OFCondition movePerFrameItems(DcmItem& item);
+
+    /** Insert/adapt attributes that are required with the merged result
+     *  instance.
+     *  @return  EC_Normal if successful, failure otherwise
+     */
+    virtual OFCondition insertDestinationAttributes();
+
+    virtual OFCondition
+    computeBytesPerFrame(const Uint16 rows, const Uint16 cols, const Uint16 bitsAlloc, size_t& bytes_per_frame);
+
+private:
+    /// Map with entries consisting each of ConcatenationUID and related
+    /// Concatenation information.
+    TScanResult m_Concats;
+
+    /// List with failed files, each entry consisting of filename, error text and
+    /// SOP Instance UID (latter might be empty).
+    TScanFailures m_FailedFiles;
+
+    /// If OFTrue, the missing of attribute SOP Instance UID of Concatenation
+    /// Source is ignored and will not lead to an error
+    OFBool m_ignoreMissingSourceUID;
+
+    /// The dataset that will contain the final merged SOP instance produced
+    /// by the load() method. Once a merged instance is provided to the caller,
+    /// as a result of load(), the caller is responsible for deleting the
+    /// related memory.
+    DcmDataset* m_Result;
+
+    /// The frames that will contain all the frames of the merged SOP instance
+    /// produced by the load() method. Once a merged instance is provided to
+    /// the caller, as a result of load(), the caller is responsible for
+    /// deleting the related memory.
+    OFVector<DcmIODTypes::Frame*> m_Frames;
+};
+
+#endif // CONCATENATIONLOADER_H
index b240d0de5bed977c8453071935866bb624c9ae0e..ddca09feb181a8ec46f714d71d8964880e135e55 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define FG_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofmap.h"
-#include "dcmtk/dcmfg/fgtypes.h"
-#include "dcmtk/dcmfg/fgbase.h"
-#include "dcmtk/dcmdata/dctagkey.h"
-#include "dcmtk/dcmdata/dcsequen.h"
 
+#include "dcmtk/dcmdata/dcsequen.h"
+#include "dcmtk/dcmdata/dctagkey.h"
+#include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/ofstd/ofmap.h"
 
 // forward declaration
 class FGBase;
@@ -40,75 +40,71 @@ class DCMTK_DCMFG_EXPORT FunctionalGroups
 {
 
 public:
-
-  /// Iterator type for iterating functional groups
-  typedef OFMap<DcmFGTypes::E_FGType, FGBase*>::iterator iterator;
-
-  /// Const iterator type for iterating functional groups
-  typedef OFMap<DcmFGTypes::E_FGType, FGBase*>::const_iterator const_iterator;
-
-  /** Constructor, creates empty set of functional groups
-   */
-  FunctionalGroups();
-
-  /** Virtual destructor, cleans up set of functional groups and
-   *  frees the related memory
-   */
-  virtual ~FunctionalGroups();
-
-  /** Cleans up set of functional groups and frees the related memory
-   */
-  virtual void clear();
-
-  /** Find a functional group by its type
-   *  @param  fgType The type of the functional group
-   *  @return The functional group, if found, NULL otherwise
-   */
-  virtual FGBase* find(const DcmFGTypes::E_FGType fgType);
-
-  /** Iterator pointing to first functional group in the set
-   *  @return First functional group in set
-   */
-  virtual FunctionalGroups::iterator begin();
-
-  /** Iterator pointing behind last functional group in the set
-   *  @return Iterator pointing behind last functional group in the set
-   */
-  virtual FunctionalGroups::iterator end();
-
-  /** Const iterator pointing to first functional group in the set
-   *  @return First functional group in set
-   */
-  virtual FunctionalGroups::const_iterator begin() const;
-
-  /** Const iterator pointing behind last functional group in the set
-   *  @return Iterator pointing behind last functional group in the set
-   */
-  virtual FunctionalGroups::const_iterator end() const;
-
-  /** Insert new functional group; ownership is taken over from caller if
-   *  function call is successful.
-   *  @param  group The group to insert
-   *  @param  replaceOld If OFTrue, then the existing functional group of the
-   *          same type (if existing) is deleted and replaced by the given one.
-   *  @return EC_Normal, if insertion was successful, error otherwise. In the
-   *          latter case, the caller keeps the ownership of the given object.
-   */
-  virtual OFCondition insert(FGBase* group,
-                             const OFBool replaceOld);
-
-  /** Remove functional group specified by its type. The memory is not
-   *  freed by the call but must freed by the caller using the returned pointer.
-   *  @param  fgType The type of the group to remove
-   *  @return The functional group removed, or NULL, if not found
-   */
-  virtual FGBase* remove(const DcmFGTypes::E_FGType fgType);
+    /// Iterator type for iterating functional groups
+    typedef OFMap<DcmFGTypes::E_FGType, FGBase*>::iterator iterator;
+
+    /// Const iterator type for iterating functional groups
+    typedef OFMap<DcmFGTypes::E_FGType, FGBase*>::const_iterator const_iterator;
+
+    /** Constructor, creates empty set of functional groups
+     */
+    FunctionalGroups();
+
+    /** Virtual destructor, cleans up set of functional groups and
+     *  frees the related memory
+     */
+    virtual ~FunctionalGroups();
+
+    /** Cleans up set of functional groups and frees the related memory
+     */
+    virtual void clear();
+
+    /** Find a functional group by its type
+     *  @param  fgType The type of the functional group
+     *  @return The functional group, if found, NULL otherwise
+     */
+    virtual FGBase* find(const DcmFGTypes::E_FGType fgType);
+
+    /** Iterator pointing to first functional group in the set
+     *  @return First functional group in set
+     */
+    virtual FunctionalGroups::iterator begin();
+
+    /** Iterator pointing behind last functional group in the set
+     *  @return Iterator pointing behind last functional group in the set
+     */
+    virtual FunctionalGroups::iterator end();
+
+    /** Const iterator pointing to first functional group in the set
+     *  @return First functional group in set
+     */
+    virtual FunctionalGroups::const_iterator begin() const;
+
+    /** Const iterator pointing behind last functional group in the set
+     *  @return Iterator pointing behind last functional group in the set
+     */
+    virtual FunctionalGroups::const_iterator end() const;
+
+    /** Insert new functional group; ownership is taken over from caller if
+     *  function call is successful.
+     *  @param  group The group to insert
+     *  @param  replaceOld If OFTrue, then the existing functional group of the
+     *          same type (if existing) is deleted and replaced by the given one.
+     *  @return EC_Normal, if insertion was successful, error otherwise. In the
+     *          latter case, the caller keeps the ownership of the given object.
+     */
+    virtual OFCondition insert(FGBase* group, const OFBool replaceOld);
+
+    /** Remove functional group specified by its type. The memory is not
+     *  freed by the call but must freed by the caller using the returned pointer.
+     *  @param  fgType The type of the group to remove
+     *  @return The functional group removed, or NULL, if not found
+     */
+    virtual FGBase* remove(const DcmFGTypes::E_FGType fgType);
 
 private:
-
-  /// Map holding the functional groups, one of each type at most
-  OFMap<DcmFGTypes::E_FGType, FGBase*> m_groups;
-
+    /// Map holding the functional groups, one of each type at most
+    OFMap<DcmFGTypes::E_FGType, FGBase*> m_groups;
 };
 
 #endif // FG_H
index 4d1645d9bfd0cf3fee43403b0424ac3dcf3e88ab..6eaf395c7a77f0b4b6341c6e045fb4f11c5af782 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define FGBASE_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofstd.h"
+
 #include "dcmtk/dcmdata/dcitem.h"
 #include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/ofstd/ofstd.h"
 
 /** Abstract base class for deriving specific functional groups
  */
@@ -33,125 +34,128 @@ class DCMTK_DCMFG_EXPORT FGBase
 {
 
 public:
-
-  /** Constructor, creates new functional group of given type.
-   *  @param  fgType The type of functional group to create
-   */
-  FGBase(const DcmFGTypes::E_FGType fgType);
-
-  /** Check whether functional group has valid and complete data
-   *  @return EC_Normal, if check is ok, error otherwise
-   */
-  virtual OFCondition check() const = 0;
-
-  /** Read functional group from given item. Old data is overwritten.
-   *  @param  item The item to read from. This must contain the sequence
-   *          element that uniquely identifies the functional group.
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& item) = 0;
-
-  /** Write functional group to given item. If the functional group already
-   *  exists it is overwritten.
-   *  @param  item The item to write to. The method will write the sequence
-   *          specific for the functional group into the item
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item) = 0;
-
-  /** Find out whether functional group is potentially only shared, only
-   *  per-frame or can be both
-   *  @return The functional group "shared type"
-   */
-  virtual DcmFGTypes::E_FGSharedType getSharedType() const =0;
-
-  /** Return the type of this functional group
-   *  @return The functional group's type
-   */
-  virtual DcmFGTypes::E_FGType getType() const;
-
-  /** Clear any data in the group
-   */
-  virtual void clearData() =0;
-
-  /** Virtual destructor
-   */
-  virtual ~FGBase();
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (e.g.\ both
-   *  FGDerivationImage) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the  first component that does not match
-   *          is lower in the rhs object, or all compared components match
-   *          but the rhs component is shorter.  Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in the rhs object, or all compared components match
-   *          but the rhs component is longer.
-   */
-  virtual int compare(const FGBase& rhs) const = 0;
-
-  /** Returns a deep copy of this object
-   *  @return  Deep copy of this object
-   */
-  virtual FGBase *clone() const = 0;
+    /** Constructor, creates new functional group of given type.
+     *  @param  fgType The type of functional group to create
+     */
+    FGBase(const DcmFGTypes::E_FGType fgType);
+
+    /** Check whether functional group has valid and complete data
+     *  @return EC_Normal, if check is ok, error otherwise
+     */
+    virtual OFCondition check() const = 0;
+
+    /** Read functional group from given item. Old data is overwritten.
+     *  @param  item The item to read from. This must contain the sequence
+     *          element that uniquely identifies the functional group.
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item) = 0;
+
+    /** Write functional group to given item. If the functional group already
+     *  exists it is overwritten.
+     *  @param  item The item to write to. The method will write the sequence
+     *          specific for the functional group into the item
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item) = 0;
+
+    /** Find out whether functional group is potentially only shared, only
+     *  per-frame or can be both
+     *  @return The functional group "shared type"
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const = 0;
+
+    /** Return the type of this functional group
+     *  @return The functional group's type
+     */
+    virtual DcmFGTypes::E_FGType getType() const;
+
+    /** Clear any data in the group
+     */
+    virtual void clearData() = 0;
+
+    /** Virtual destructor
+     */
+    virtual ~FGBase();
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (e.g.\ both
+     *  FGDerivationImage) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the  first component that does not match
+     *          is lower in the rhs object, or all compared components match
+     *          but the rhs component is shorter.  Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in the rhs object, or all compared components match
+     *          but the rhs component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const = 0;
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const = 0;
 
 protected:
-
-  /** Get the item containing the payload of a functional group sequence,
-   *  identified by the functional group's sequence key provided and the desired
-   *  item number.
-   *  @param  source The item to read the sequence from, e.g.\ item of the
-   *          Shared Functional Group Sequence
-   *  @param  seqKey The identifying key of the functional group's sequence
-   *  @param  itemNum The item number to get from that sequence (usually,
-   *          a functional group has exactly a single item, i.e.\ the parameter
-   *          would be set to 0
-   *  @param  result The item if found, otherwise NULL
-   *  @return EC_Normal, if specified item could be retrieved, error otherwise
-   */
-  virtual OFCondition getItemFromFGSequence(DcmItem& source,
+    /** Get the item containing the payload of a functional group sequence,
+     *  identified by the functional group's sequence key provided and the desired
+     *  item number.
+     *  @param  source The item to read the sequence from, e.g.\ item of the
+     *          Shared Functional Group Sequence
+     *  @param  seqKey The identifying key of the functional group's sequence
+     *  @param  itemNum The item number to get from that sequence (usually,
+     *          a functional group has exactly a single item, i.e.\ the parameter
+     *          would be set to 0
+     *  @param  result The item if found, otherwise NULL
+     *  @return EC_Normal, if specified item could be retrieved, error otherwise
+     */
+    virtual OFCondition
+    getItemFromFGSequence(DcmItem& source, const DcmTagKey& seqKey, const unsigned long itemNum, DcmItem*& result);
+
+    /** Get number of items in a functional group sequence, identified by the functional
+     *  group's sequence key.
+     *  @param  source The item to read the sequence from, e.g.\ item of the
+     *          Shared Functional Group Sequence
+     *  @param  seqKey The identifying key of the functional group's sequence
+     *  @param  result The number of items found
+     *  @return EC_Normal, if number could be retrieved, error otherwise
+     */
+    virtual OFCondition getNumItemsFromFGSequence(DcmItem& source, const DcmTagKey& seqKey, unsigned long& result);
+
+    /** Create functional group sequence specified by given sequence tag key
+     *  @param  destination The item to put the sequence into
+     *  @param  seqKey The functional group's tag key
+     *  @param  numItems The number of items to create within sequence (minus 1).
+     *          Usually, functional group only contain a single item,
+     *          i.e.\ numItems would be set to 0
+     *  @param  firstItem Reference to the first item the method created
+     *  @return EC_Normal if creation was successful, error otherwise
+     */
+    virtual OFCondition createNewFGSequence(DcmItem& destination,
                                             const DcmTagKey& seqKey,
-                                            const unsigned long itemNum,
-                                            DcmItem*& result);
-
-  /** Create functional group sequence specified by given sequence tag key
-   *  @param  destination The item to put the sequence into
-   *  @param  seqKey The functional group's tag key
-   *  @param  numItems The number of items to create within sequence (minus 1).
-   *          Usually, functional group only contain a single item,
-   *          i.e.\ numItems would be set to 0
-   *  @param  firstItem Reference to the first item the method created
-   *  @return EC_Normal if creation was successful, error otherwise
-   */
-  virtual OFCondition createNewFGSequence(DcmItem& destination,
-                                          const DcmTagKey& seqKey,
-                                          const unsigned long numItems,
-                                          DcmItem*& firstItem);
+                                            const unsigned long numItems,
+                                            DcmItem*& firstItem);
 
 private:
+    /// Private default constructor, shall not be used
+    FGBase();
 
-  /// Private default constructor, shall not be used
-  FGBase();
-
-  /// The type of the functional group
-  DcmFGTypes::E_FGType m_fgType;
-
+    /// The type of the functional group
+    DcmFGTypes::E_FGType m_fgType;
 };
 
-
 /** Class representing an "unknown" functional group, e.g.\ a private one
  *  specified by a vendor or one that is not explicitly known yet to the
  *  dcmfg library.
@@ -163,107 +167,110 @@ class DCMTK_DCMFG_EXPORT FGUnknown : public FGBase
 {
 
 public:
-
-  /** Creates unknown (to the dcmfg class library) functional group
-   *  @param seqStartTag The tag that uniquely identifies this functional group
-   *  @param sharedType Defines whether this group is potentially per-frame,
-   *         shared or can be both. Default is "unknown".
-   */
-  FGUnknown(const DcmTagKey& seqStartTag,
-            const DcmFGTypes::E_FGSharedType sharedType = DcmFGTypes::EFGS_UNKNOWN);
-
-  /** Copy constructor, performs a deep copy of the given object.
-   *  @param rhs The functional group to initialize from
-   */
-  FGUnknown(const FGUnknown& rhs);
-
-  /** Assignment operator, performs a deep copy for assigning given object.
-   *  @param  rhs The functional group to assign from
-   *  @return Reference to this object
-   */
-  FGUnknown& operator=(const FGUnknown& rhs);
-
-  /** Returns type of this functional group (always "EFG_UNKNOWN")
-   *  @return Always returns DcmFGTypes::EFG_UNKNOWN
-   */
-  virtual DcmFGTypes::E_FGType getType() const {return DcmFGTypes::EFG_UNKNOWN;}
-
-  /** Returns whether this group is potentially per-frame, shared or can be both
-   *  @return The functional group's "shared type"
-   */
-  virtual DcmFGTypes::E_FGSharedType getSharedType() const {return m_sharedType;}
-
-  /** Returns a deep copy of this object
-   *  @return  Deep copy of this object
-   */
-  virtual FGBase *clone() const;
-
-  /** Check whether this functional group contains valid data
-   *  @returns EC_Normal if functional group is valid. For now, always returns
-   *           EC_Normal
-   */
-  virtual OFCondition check() const;
-
-  /** Clear data within this group
-   */
-  virtual void clearData();
-
-  /** Read this group into memory
-   *  @param  item The item to read from
-   */
-  virtual OFCondition read(DcmItem& item);
-
-  /** Write this group to given item
-   *  @param  item The item to write to
-   */
-  virtual OFCondition write(DcmItem& item);
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGUnknown) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the this object, or all compared components match
-   *          but this component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in this object, or all compared components match
-   *          but this component is longer.
-   */
-  virtual int compare(const FGBase& rhs) const;
-
-  /** Virtual destructor, frees memory
-   */
-  virtual ~FGUnknown();
+    /** Creates unknown (to the dcmfg class library) functional group
+     *  @param seqStartTag The tag that uniquely identifies this functional group
+     *  @param sharedType Defines whether this group is potentially per-frame,
+     *         shared or can be both. Default is "unknown".
+     */
+    FGUnknown(const DcmTagKey& seqStartTag, const DcmFGTypes::E_FGSharedType sharedType = DcmFGTypes::EFGS_UNKNOWN);
+
+    /** Copy constructor, performs a deep copy of the given object.
+     *  @param rhs The functional group to initialize from
+     */
+    FGUnknown(const FGUnknown& rhs);
+
+    /** Assignment operator, performs a deep copy for assigning given object.
+     *  @param  rhs The functional group to assign from
+     *  @return Reference to this object
+     */
+    FGUnknown& operator=(const FGUnknown& rhs);
+
+    /** Returns type of this functional group (always "EFG_UNKNOWN")
+     *  @return Always returns DcmFGTypes::EFG_UNKNOWN
+     */
+    virtual DcmFGTypes::E_FGType getType() const
+    {
+        return DcmFGTypes::EFG_UNKNOWN;
+    }
+
+    /** Returns whether this group is potentially per-frame, shared or can be both
+     *  @return The functional group's "shared type"
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return m_sharedType;
+    }
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Check whether this functional group contains valid data
+     *  @returns EC_Normal if functional group is valid. For now, always returns
+     *           EC_Normal
+     */
+    virtual OFCondition check() const;
+
+    /** Clear data within this group
+     */
+    virtual void clearData();
+
+    /** Read this group into memory
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error code otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Write this group to given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error code otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    /** Virtual destructor, frees memory
+     */
+    virtual ~FGUnknown();
 
 private:
+    /** Private default constructor, shall not be used
+     */
+    FGUnknown();
 
-  /** Private default constructor, shall not be used
-   */
-  FGUnknown();
+    /// The tag that uniquely identifies this functional group
+    DcmTagKey m_seqStartTag;
 
-  /// The tag that uniquely identifies this functional group
-  DcmTagKey m_seqStartTag;
-
-  /// The data hold by this item, i.e.\ the sequence making up the functional
-  /// group
-  DcmSequenceOfItems* m_fgSequence;
-
-  /// Denotes whether this group is potentially per-frame, shared or can be both
-  DcmFGTypes::E_FGSharedType m_sharedType;
+    /// The data hold by this item, i.e.\ the sequence making up the functional
+    /// group
+    DcmSequenceOfItems* m_fgSequence;
 
+    /// Denotes whether this group is potentially per-frame, shared or can be both
+    DcmFGTypes::E_FGSharedType m_sharedType;
 };
 
 #endif // FGBASE_H
-
diff --git a/dcmfg/include/dcmtk/dcmfg/fgctacquisitiondetails.h b/dcmfg/include/dcmtk/dcmfg/fgctacquisitiondetails.h
new file mode 100644 (file)
index 0000000..3957293
--- /dev/null
@@ -0,0 +1,373 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT Acquisition Details Functional Group
+ *
+ */
+
+#ifndef FGCTACQUISITIONDETAILS_H
+#define FGCTACQUISITIONDETAILS_H
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dctk.h"
+#include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/ofstd/ofstring.h"
+#include "dcmtk/ofstd/ofvector.h"
+
+/** Class representing the "CT Acquisition Details" Functional Group Macro.
+ */
+class DCMTK_DCMFG_EXPORT FGCTAcquisitionDetails : public FGBase
+{
+public:
+    enum E_RotationDirection
+    {
+        E_RotationDirection_CC,
+        E_RotationDirection_CW,
+        E_RotationDirection_Empty,
+        E_RotationDirection_Invalid
+    };
+
+    /** Constructor, creates empty functional group
+     */
+    FGCTAcquisitionDetails();
+
+    /** Class representing an item of the "CT Acquisition Details " Functional Group Macro.
+     */
+    class DCMTK_DCMFG_EXPORT FGCTAcquisitionDetailsItem
+    {
+    public:
+        /** Constructor
+         */
+        FGCTAcquisitionDetailsItem();
+
+        /** Virtual destructor
+         */
+        virtual ~FGCTAcquisitionDetailsItem();
+
+        /** Returns a deep copy of this object
+         *  @return  Deep copy of this object
+         */
+        virtual FGCTAcquisitionDetailsItem* clone() const;
+
+        /** Clear all data
+         */
+        virtual void clearData();
+
+        /** Check whether the current content of this group is consistent and complete
+         *  @return EC_Normal, if no errors are found, error otherwise
+         */
+        virtual OFCondition check() const;
+
+        /** Read CT Acquisition Details Sequence item from given dataitem
+         *  @param  item The item to read from
+         *  @return EC_Normal if reading was successful, error otherwise
+         */
+        virtual OFCondition read(DcmItem& item);
+
+        /** Writes the content of this class into CT Acquisition Details Sequence item
+         *  (newly created) into given item
+         *  @param  item The item to write to
+         *  @return EC_Normal if writing was successful, error otherwise
+         */
+        virtual OFCondition write(DcmItem& item);
+
+        /** Comparison operator that compares the normalized value of this object
+         *  with a given object of the same type, i.e.\ the elements within both
+         *  functional groups (this and rhs parameter) are compared by value!
+         *  Both objects (this and rhs) need to have the same type (i.e.\ both
+         *  FGUnknown) to be comparable. This function is used in order
+         *  to decide whether a functional group already exists, or is new. This
+         *  is used in particular to find out whether a given functional group
+         *  can be shared (i.e.\ the same information already exists as shared
+         *  functional group) or is different from the same shared group. In that
+         *  case the shared functional group must be distributed into per-frame
+         *  functional groups, instead. The exact implementation for implementing
+         *  the comparison is not relevant. However, it must be a comparison
+         *  by value.
+         *  @param  rhs the right hand side of the comparison
+         *  @return 0 if the object values are equal.
+         *          -1 if either the value of the first component that does not match
+         *          is lower in the this object, or all compared components match
+         *          but this component is shorter. Also returned if this type and
+         *          rhs type (DcmFGTypes::E_FGType) do not match.
+         *          1 if either the value of the first component that does not match
+         *          is greater in this object, or all compared components match
+         *          but this component is longer.
+         */
+        virtual int compare(const FGCTAcquisitionDetailsItem& rhs) const;
+
+        // --- get() functionality ---
+
+        /** Get Referenced Path Index
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Position of the value inside the DICOM element. If 0, the first
+         *          value is returned. If the no value at the given position exists,
+         *          an error is returned.
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getReferencedPathIndex(Uint16& value, const unsigned long pos = 0);
+
+        /** Get Referenced Path Index
+         *  @param  values Reference to variable that should hold the result
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getReferencedPathIndex(OFVector<Uint16>& values);
+
+        /** Get Rotation Direction
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getRotationDirection(OFString& value, const signed long pos = 0);
+
+        /** Get Rotation Direction
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Position of the value inside the DICOM element. If 0, the first
+         *          value is returned. If the no value at the given position exists,
+         *          an error is returned.
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getRotationDirection(E_RotationDirection& value, const signed long pos = 0);
+
+        /** Get Revolution Time
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Position of the value inside the DICOM element. If 0, the first
+         *          value is returned. If the no value at the given position exists,
+         *          an error is returned.
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getRevolutionTime(Float64& value, const unsigned long pos = 0);
+
+        /** Get Single Collimation Width
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Position of the value inside the DICOM element. If 0, the first
+         *          value is returned. If the no value at the given position exists,
+         *          an error is returned.
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getSingleCollimationWidth(Float64& value, const unsigned long pos = 0);
+
+        /** Get Total Collimation Width
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Position of the value inside the DICOM element. If 0, the first
+         *          value is returned. If the no value at the given position exists,
+         *          an error is returned.
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getTotalCollimationWidth(Float64& value, const unsigned long pos = 0);
+
+        /** Get Table Height
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Position of the value inside the DICOM element. If 0, the first
+         *          value is returned. If the no value at the given position exists,
+         *          an error is returned.
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getTableHeight(Float64& value, const unsigned long pos = 0);
+
+        /** Get Gantry Detector Tilt
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Position of the value inside the DICOM element. If 0, the first
+         *          value is returned. If the no value at the given position exists,
+         *          an error is returned.
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getGantryDetectorTilt(Float64& value, const unsigned long pos = 0);
+
+        /** Get Data Collection Diameter
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Position of the value inside the DICOM element. If 0, the first
+         *          value is returned. If the no value at the given position exists,
+         *          an error is returned.
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getDataCollectionDiameter(Float64& value, const unsigned long pos = 0);
+
+        // --- set() functionality ---
+
+        /** Set Referenced Path Index
+         *  @param  values Values that should be set
+         *  @param  checkValues Check 'values'. Not evaluated (here for consistency
+         *          with other setter functions).
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setReferencedPathIndex(const OFVector<Uint16>& values, const OFBool checkValues = OFTrue);
+
+        /** Set Rotation Direction
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setRotationDirection(const E_RotationDirection& value, const OFBool checkValue = OFTrue);
+
+        /** Set Revolution Time
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setRevolutionTime(const Float64 value, const OFBool checkValue = OFTrue);
+
+        /** Set Single Collimation Width
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setSingleCollimationWidth(const Float64 value, const OFBool checkValue = OFTrue);
+
+        /** Set Total Collimation Width
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setTotalCollimationWidth(const Float64 value, const OFBool checkValue = OFTrue);
+
+        /** Set Table Height
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setTableHeight(const Float64 value, const OFBool checkValue = OFTrue);
+
+        /** Set Gantry/Detector Tilt
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setGantryDetectorTilt(const Float64 value, const OFBool checkValue = OFTrue);
+
+        /** Set Data Collection Diameter
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setDataCollectionDiameter(const Float64 value, const OFBool checkValue = OFTrue);
+
+        static E_RotationDirection rotaDir2Enum(const OFString& str);
+
+        static OFBool rotaDir2Str(const E_RotationDirection& rota, OFString& result);
+
+    private:
+        /* Content of CT Acquisition Details Macro (item) */
+
+        /// Referenced Path Index (US, VM 1-n, Required type 1C)
+        DcmUnsignedShort m_ReferencedPathIndex;
+
+        /// Rotation Direction (CS, 1, 1C)
+        DcmCodeString m_RotationDirection;
+
+        /// Revolution Time (FD, 1, 1C)
+        DcmFloatingPointDouble m_RevolutionTime;
+
+        /// Single Collimation Width (FD, 1, 1C)
+        DcmFloatingPointDouble m_SingleCollimationWidth;
+
+        /// Total Collimation Width  (FD, 1, 1C)
+        DcmFloatingPointDouble m_TotalCollimationWidth;
+
+        /// Table Height (DS, 1, 1C)
+        DcmDecimalString m_TableHeight;
+
+        /// Gantry/Detector Tilt (DS, 1, 1C)
+        DcmDecimalString m_GantryDetectorTilt;
+
+        /// Data Collection Diameter (DS, 1, 1C)
+        DcmDecimalString m_DataCollectionDiameter;
+    };
+
+    /** Virtual destructor
+     */
+    virtual ~FGCTAcquisitionDetails();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Returns shared functional group type
+     *  @return The functional group type (DcmFGTypes::EFGS_BOTH)
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clear all data
+     */
+    virtual void clearData();
+
+    /** Check whether the current content of this group is consistent and complete
+     *  @return EC_Normal, if no errors are found, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read CT Acquisition Details Sequence from given item
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Writes the content of this class into CT Acquisition Details Sequence
+     *  (newly cerated) into given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    // --- get() functionality ---
+
+    OFVector<FGCTAcquisitionDetailsItem*>& getCTAcquisitionDetailsItems();
+
+private:
+    /* Content of CT Acquisition Details Macro */
+
+    OFVector<FGCTAcquisitionDetailsItem*> m_Items;
+};
+
+#endif // FGCTACQUISITIONDETAILS_H
diff --git a/dcmfg/include/dcmtk/dcmfg/fgctacquisitiontype.h b/dcmfg/include/dcmtk/dcmfg/fgctacquisitiontype.h
new file mode 100644 (file)
index 0000000..084cb09
--- /dev/null
@@ -0,0 +1,247 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT Acquisition Type Functional Group
+ *
+ */
+
+#ifndef FGCTACQUISITIONTYPE_H
+#define FGCTACQUISITIONTYPE_H
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dctk.h"
+#include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/ofstd/ofstring.h"
+#include "dcmtk/ofstd/ofvector.h"
+
+/** Class representing the "CT Acquisition Type" Functional Group Macro.
+ */
+class DCMTK_DCMFG_EXPORT FGCTAcquisitionType : public FGBase
+{
+public:
+    static const OFString DT_AcquisitionType_Sequenced;
+    static const OFString DT_AcquisitionType_Spiral;
+    static const OFString DT_AcquisitionType_ConstantAngle;
+    static const OFString DT_AcquisitionType_Stationary;
+    static const OFString DT_AcquisitionType_Free;
+
+    enum E_ConstantVolumeFlag
+    {
+        E_ConstVol_Yes,
+        E_ConstVol_No,
+        E_ConstVol_Empty,
+        E_ConstVol_Invalid
+    };
+
+    enum E_FluoroscopyFlag
+    {
+        E_Fluoroscopy_Yes,
+        E_Fluoroscopy_No,
+        E_Fluoroscopy_Empty,
+        E_Fluoroscopy_Invalid
+    };
+
+    /** Constructor, creates empty functional group
+     */
+    FGCTAcquisitionType();
+
+    /** Virtual destructor
+     */
+    virtual ~FGCTAcquisitionType();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Returns shared functional group type
+     *  @return The functional group type (DcmFGTypes::EFGS_BOTH)
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clear all data
+     */
+    virtual void clearData();
+
+    /** Check whether the current content of this group is consistent and complete
+     *  @return EC_Normal, if no errors are found, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read CT Acquisition Type Sequence from given item
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Writes the content of this class into CT Acquisition Type Sequence
+     *  (newly cerated) into given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    // --- get() functionality ---
+
+    /** Get Acquisition Type
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getAcquisitionType(OFString& value, const signed long pos = 0);
+
+    /** Get Tube Angle
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Position of the value inside the DICOM element. If 0, the first
+     *          value is returned. If the no value at the given position exists,
+     *          an error is returned.
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getTubeAngle(Float64& value, const unsigned long pos = 0);
+
+    /** Get Constant Value Flag
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getConstantVolumeFlag(OFString& value, const signed long pos = 0);
+
+    /** Get Constant Value Flag
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getConstantVolumeFlag(E_ConstantVolumeFlag& value, const signed long pos = 0);
+
+    /** Get Fluoroscopy Flag
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getFluoroscopyFlag(OFString& value, const signed long pos = 0);
+
+    /** Get Fluoroscopy Flag
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getFluoroscopyFlag(E_FluoroscopyFlag& value, const signed long pos = 0);
+
+    // --- set() functionality ---
+
+    /** Set Acquisition Type
+     *  @param  value Value that should be set
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setAcquisitionType(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Tube Angle
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setTubeAngle(const Float64& value, const OFBool checkValue = OFTrue);
+
+    /** Set Constant Volume Flag
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setConstantVolumeFlag(const E_ConstantVolumeFlag& value, const OFBool checkValue = OFTrue);
+
+    /** Set Constant Volume Flag
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setConstantVolumeFlag(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Fluoroscopy Flag
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setFluoroscopyFlag(const E_FluoroscopyFlag& value, const OFBool checkValue = OFTrue);
+
+    /** Set Fluoroscopy Flag
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setFluoroscopyFlag(const OFString& value, const OFBool checkValue = OFTrue);
+
+    static E_ConstantVolumeFlag constVolFlag2Enum(const OFString& str);
+
+    static OFBool constVolFlag2Str(const E_ConstantVolumeFlag& eval, OFString& result);
+
+    static E_FluoroscopyFlag fluoroscopyFlag2Enum(const OFString& str);
+
+    static OFBool fluoroscopyFlag2Str(const E_FluoroscopyFlag& eval, OFString& result);
+
+private:
+    /* Content of CT Acquisition Type Macro */
+
+    /// Acquisition Type (CS, VM 1, Required type 1)
+    DcmCodeString m_AcquisitionType;
+
+    /// Tube Angle (FD, 1, 1)
+    DcmFloatingPointDouble m_TubeAngle;
+
+    /// Constant Volume Flag (CS, 1, 1)
+    DcmCodeString m_ConstantVolumeFlag;
+
+    /// Fluoroscopy Flag (CS, 1, 1)
+    DcmCodeString m_FluoroscopyFlag;
+};
+
+#endif // FGCTACQUISITIONTYPE_H
diff --git a/dcmfg/include/dcmtk/dcmfg/fgctadditionalxraysource.h b/dcmfg/include/dcmtk/dcmfg/fgctadditionalxraysource.h
new file mode 100644 (file)
index 0000000..9d2ab44
--- /dev/null
@@ -0,0 +1,371 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT Additional X-Ray Source Functional Group
+ *
+ */
+
+#ifndef FGCTADDITIONALXRAYSOURCE_H
+#define FGCTADDITIONALXRAYSOURCE_H
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dcitem.h"
+#include "dcmtk/dcmdata/dctk.h" // TODO: include only needed VRs
+#include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/dcmfg/fgdefine.h"
+
+/** Class representing the CT Additional X-Ray Source Functional Group Macro.
+ */
+class DCMTK_DCMFG_EXPORT FGCTAdditionalXRaySource : public FGBase
+{
+public:
+    /** Constructor, creates empty CT Additional X-Ray Source Functional Group
+     */
+    FGCTAdditionalXRaySource();
+
+    /** Destructor, frees memory
+     */
+    virtual ~FGCTAdditionalXRaySource();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Get shared type of this functional group (can be both, per-frame and
+     *  shared)
+     *  @return Always returns EFGS_BOTH
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Check whether functional group contains valid data
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Clears all data
+     */
+    virtual void clearData();
+
+    /** Read functional group from given item, i.e.\ read CT Additional X-Ray Source Sequence
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Write functional group to given item, i.e.\ write CT Additional X-Ray Source Sequence
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    /** Class representing an item of the "CT Additional X-Ray Source" Functional Group Macro.
+     */
+    class DCMTK_DCMFG_EXPORT FGCTAdditionalXRaySourceItem
+    {
+    public:
+        /** Constructor, creates empty CT Additional X-Ray Source Functional Group
+         */
+        FGCTAdditionalXRaySourceItem();
+
+        /** Destructor, frees memory
+         */
+        virtual ~FGCTAdditionalXRaySourceItem();
+
+        /** Returns a deep copy of this object
+         *  @return  Deep copy of this object
+         */
+        virtual FGCTAdditionalXRaySourceItem* clone() const;
+
+        /** Clears all data
+         */
+        virtual void clearData();
+
+        /** Check whether functional group contains valid data
+         *  @return EC_Normal if data is valid, error otherwise
+         */
+        virtual OFCondition check() const;
+
+        /** Read functional group from given item, i.e.\ read CT Additional X-Ray Source Sequence
+         *  @param  item The item to read from
+         *  @return EC_Normal if reading was successful, error otherwise
+         */
+        virtual OFCondition read(DcmItem& item);
+
+        /** Write functional group to given item, i.e.\ write CT Additional X-Ray Source Sequence
+         *  @param  item The item to write to
+         *  @return EC_Normal if writing was successful, error otherwise
+         */
+        virtual OFCondition write(DcmItem& item);
+
+        /** Get KVP
+         *  Peak kilo voltage output of the X-Ray generator used.
+         *  @param  value Reference to variable in which the value should be stored
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition getKVP(OFString& value, const signed long pos = 0) const;
+
+        /** Get XRayTubeCurrentInmA
+         *  Nominal X-Ray tube current in milliamperes.
+         *  @param  value Reference to variable in which the value should be stored
+         *  @param  pos Index of the value to get (0..vm-1)
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition getXRayTubeCurrentInmA(Float64& value, const unsigned long pos = 0) const;
+
+        /** Get DataCollectionDiameter
+         *  The diameter in mm of the region over which data were collected.
+         *  @param  value Reference to variable in which the value should be stored
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition getDataCollectionDiameter(OFString& value, const signed long pos = 0) const;
+
+        /** Get FocalSpots
+         *  Used nominal size of the focal spot in mm.
+         *  @param  value Reference to variable in which the value should be stored
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition getFocalSpots(OFString& value, const signed long pos = 0) const;
+
+        /** Get FilterType
+         *  Type of filter(s) inserted into the X-Ray beam. See
+         *  @param  value Reference to variable in which the value should be stored
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition getFilterType(OFString& value, const signed long pos = 0) const;
+
+        /** Get FilterMaterial
+         *  The X-Ray absorbing material used in the filter.
+         *  @param  value Reference to variable in which the value should be stored
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition getFilterMaterial(OFString& value, const signed long pos = 0) const;
+
+        /** Get ExposureInmAs
+         *  The exposure expressed in milliampere seconds, for example calculated from exposure time and X-Ray tube
+         * current.
+         *  @param  value Reference to variable in which the value should be stored
+         *  @param  pos Index of the value to get (0..vm-1)
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition getExposureInmAs(Float64& value, const unsigned long pos = 0) const;
+
+        /** Get EnergyWeightingFactor
+         *  The weighting factor of the data from this additional source in a multiple energy composition image. This
+         * factor incorporates the effects ofRequired if Required if Frame Type (0008,9007) Value 4 of this frame is
+         * ENERGY_PROP_WT. May be present otherwise.
+         *  @param  value Reference to variable in which the value should be stored
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition getEnergyWeightingFactor(Float32& value, const unsigned long pos = 0) const;
+
+        /** Set KVP
+         *  Peak kilo voltage output of the X-Ray generator used.
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1) if enabled
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setKVP(const OFString& value, const OFBool checkValue = OFTrue);
+
+        /** Set KVP
+         *  Peak kilo voltage output of the X-Ray generator used.
+         *  @param  value Value to be set
+         *  @param  checkValue Check 'value' if enabled
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setKVP(const Float64 value, const OFBool checkValue = OFTrue);
+
+        /** Set XRayTubeCurrentInmA
+         *  Nominal X-Ray tube current in milliamperes.
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value' for conformance with VR (FD) and VM (1) if enabled
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setXRayTubeCurrentInmA(const Float64 value, const OFBool checkValue = OFTrue);
+
+        /** Set DataCollectionDiameter
+         *  The diameter in mm of the region over which data were collected.
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1) if enabled
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setDataCollectionDiameter(const OFString& value, const OFBool checkValue = OFTrue);
+
+        /** Set DataCollectionDiameter
+         *  The diameter in mm of the region over which data were collected.
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1) if enabled
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setDataCollectionDiameter(const Float64 value, const OFBool checkValue = OFTrue);
+
+        /** Set FocalSpots
+         *  Used nominal size of the focal spot in mm.
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1-n) if enabled
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setFocalSpots(const OFString& value, const OFBool checkValue = OFTrue);
+
+        /** Set FocalSpots
+         *  Used nominal size of the focal spot in mm.
+         *  @param  values Values to be set
+         *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1-n) if enabled
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setFocalSpots(const OFVector<Float64>& values, const OFBool checkValue = OFTrue);
+
+        /** Set FilterType
+         *  Type of filter(s) inserted into the X-Ray beam. See
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value' for conformance with VR (SH) and VM (1) if enabled
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setFilterType(const OFString& value, const OFBool checkValue = OFTrue);
+
+        /** Set FilterMaterial
+         *  The X-Ray absorbing material used in the filter.
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1-n) if enabled
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setFilterMaterial(const OFString& value, const OFBool checkValue = OFTrue);
+
+        /** Set ExposureInmAs
+         *  The exposure expressed in milliampere seconds, for example calculated from exposure time and X-Ray tube
+         * current.
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value' for conformance with VR (FD) and VM (1) if enabled
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setExposureInmAs(const Float64 value, const OFBool checkValue = OFTrue);
+
+        /** Set EnergyWeightingFactor
+         *  The weighting factor of the data from this additional source in a multiple energy composition image. This
+         * factor incorporates the effects ofRequired if Required if Frame Type (0008,9007) Value 4 of this frame is
+         * ENERGY_PROP_WT. May be present otherwise.
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value' for conformance with VR (FL) and VM (1) if enabled
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setEnergyWeightingFactor(const Float32 value, const OFBool checkValue = OFTrue);
+
+        /** Comparison operator that compares the normalized value of this object
+         *  with a given object of the same type, i.e.\ the elements within both
+         *  functional groups (this and rhs parameter) are compared by value!
+         *  Both objects (this and rhs) need to have the same type (i.e.\ both
+         *  FGUnknown) to be comparable. This function is used in order
+         *  to decide whether a functional group already exists, or is new. This
+         *  is used in particular to find out whether a given functional group
+         *  can be shared (i.e.\ the same information already exists as shared
+         *  functional group) or is different from the same shared group. In that
+         *  case the shared functional group must be distributed into per-frame
+         *  functional groups, instead. The exact implementation for implementing
+         *  the comparison is not relevant. However, it must be a comparison
+         *  by value.
+         *  @param  rhs the right hand side of the comparison
+         *  @return 0 if the object values are equal.
+         *          -1 if either the value of the first component that does not match
+         *          is lower in the this object, or all compared components match
+         *          but this component is shorter.
+         *          1 if either the value of the first component that does not match
+         *          is greater in this object, or all compared components match
+         *          but this component is longer.
+         */
+        virtual int compare(const FGCTAdditionalXRaySourceItem& rhs) const;
+
+    protected:
+        /* Content of CT Additional X-Ray Source Functional Group Macro */
+
+        /// KVP (DS, VM 1, Required type 1)
+        /// Peak kilo voltage output of the X-Ray generator used.
+        DcmDecimalString m_KVP;
+
+        /// XRayTubeCurrentInmA (FD, VM 1, Required type 1)
+        /// Nominal X-Ray tube current in milliamperes.
+        DcmFloatingPointDouble m_XRayTubeCurrentInmA;
+
+        /// DataCollectionDiameter (DS, VM 1, Required type 1)
+        /// The diameter in mm of the region over which data were collected.
+        DcmDecimalString m_DataCollectionDiameter;
+
+        /// FocalSpots (DS, VM 1-n, Required type 1)
+        /// Used nominal size of the focal spot in mm.
+        DcmDecimalString m_FocalSpots;
+
+        /// FilterType (SH, VM 1, Required type 1)
+        /// Type of filter(s) inserted into the X-Ray beam. See
+        DcmShortString m_FilterType;
+
+        /// FilterMaterial (CS, VM 1-n, Required type 1)
+        /// The X-Ray absorbing material used in the filter.
+        DcmCodeString m_FilterMaterial;
+
+        /// ExposureInmAs (FD, VM 1, Required type 1)
+        /// The exposure expressed in milliampere seconds, for example calculated from exposure time and X-Ray tube
+        /// current.
+        DcmFloatingPointDouble m_ExposureInmAs;
+
+        /// EnergyWeightingFactor (FL, VM 1, Required type 1C)
+        /// The weighting factor of the data from this additional source in a multiple energy composition image. This
+        /// factor incorporates the effects ofRequired if Required if Frame Type (0008,9007) Value 4 of this frame is
+        /// ENERGY_PROP_WT. May be present otherwise.
+        DcmFloatingPointSingle m_EnergyWeightingFactor;
+    };
+
+    virtual OFVector<FGCTAdditionalXRaySourceItem*>& getCTAdditionalXRaySourceItems();
+
+protected:
+    OFVector<FGCTAdditionalXRaySourceItem*> m_Items;
+};
+
+#endif // FGCTADDITIONALXRAYSOURCE_H
diff --git a/dcmfg/include/dcmtk/dcmfg/fgctexposure.h b/dcmfg/include/dcmtk/dcmfg/fgctexposure.h
new file mode 100644 (file)
index 0000000..18f2034
--- /dev/null
@@ -0,0 +1,419 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT Exposure Functional Group
+ *
+ */
+
+#ifndef FGCTEXPOSURE_H
+#define FGCTEXPOSURE_H
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dctk.h"
+#include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/dcmiod/iodmacro.h"
+#include "dcmtk/ofstd/ofstring.h"
+#include "dcmtk/ofstd/ofvector.h"
+
+/** Class representing the "CT Exposure" Functional Group Macro.
+ */
+class DCMTK_DCMFG_EXPORT FGCTExposure : public FGBase
+{
+public:
+    /** Constructor, creates empty functional group
+     */
+    FGCTExposure();
+
+    /** Copy Constructor, creates deep copy
+     *  @param  rhs The object to copy from
+     */
+    FGCTExposure(const FGCTExposure& rhs);
+
+    /** Virtual destructor
+     */
+    virtual ~FGCTExposure();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Returns shared functional group type
+     *  @return The functional group type (DcmFGTypes::EFGS_BOTH)
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clear all data
+     */
+    virtual void clearData();
+
+    /** Check whether the current content of this group is consistent and complete
+     *  @return EC_Normal, if no errors are found, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read CT Exposure Sequence from given item
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Writes the content of this class into CT Exposure Sequence
+     *  (newly created) into given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    /** Class representing the "CT Exposure" Functional Group Macro item
+     */
+    class DCMTK_DCMFG_EXPORT FGCTExposureItem
+    {
+    public:
+        /** Constructor, creates empty functional group item
+         */
+        FGCTExposureItem();
+
+        /** Copy Constructor, creates deep copy
+         *  @param  rhs The object to copy from
+         */
+        FGCTExposureItem(const FGCTExposureItem& rhs);
+
+        /** Virtual destructor
+         */
+        virtual ~FGCTExposureItem();
+
+        /** Returns a deep copy of this object
+         *  @return  Deep copy of this object
+         */
+        virtual FGCTExposureItem* clone() const;
+
+        /** Clear all data
+         */
+        virtual void clearData();
+
+        /** Check whether the current content of this group is consistent and complete
+         *  @return EC_Normal, if no errors are found, error otherwise
+         */
+        virtual OFCondition check() const;
+
+        /** Read CT Exposure Sequence item from given item
+         *  @param  item The item to read from
+         *  @return EC_Normal if reading was successful, error otherwise
+         */
+        virtual OFCondition read(DcmItem& item);
+
+        /** Writes the content of this class into given item
+         *  @param  item The item to write to
+         *  @return EC_Normal if writing was successful, error otherwise
+         */
+        virtual OFCondition write(DcmItem& item);
+
+        /** Comparison operator that compares the normalized value of this object
+         *  with a given object of the same type, i.e.\ the elements within both
+         *  functional groups (this and rhs parameter) are compared by value!
+         *  Both objects (this and rhs) need to have the same type (i.e.\ both
+         *  FGUnknown) to be comparable. This function is used in order
+         *  to decide whether a functional group already exists, or is new. This
+         *  is used in particular to find out whether a given functional group
+         *  can be shared (i.e.\ the same information already exists as shared
+         *  functional group) or is different from the same shared group. In that
+         *  case the shared functional group must be distributed into per-frame
+         *  functional groups, instead. The exact implementation for implementing
+         *  the comparison is not relevant. However, it must be a comparison
+         *  by value.
+         *  @param  rhs the right hand side of the comparison
+         *  @return 0 if the object values are equal.
+         *          -1 if either the value of the first component that does not match
+         *          is lower in the this object, or all compared components match
+         *          but this component is shorter. Also returned if this type and
+         *          rhs type (DcmFGTypes::E_FGType) do not match.
+         *          1 if either the value of the first component that does not match
+         *          is greater in this object, or all compared components match
+         *          but this component is longer.
+         */
+        virtual int compare(const FGCTExposureItem& rhs) const;
+
+        // --- get() functionality ---
+
+        /** Get Referenced Path Index
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getReferencedPathIndex(OFString& value, const signed long pos = 0);
+
+        /** Get Exposure Time in ms
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getExposureTimeInMs(OFString& value, const signed long pos = 0);
+
+        /** Get Exposure Time in ms
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1)
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getExposureTimeInMs(Float64& value, const unsigned long pos = 0);
+
+        /** Get X-Ray Tube Current in mA
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getXRayTubeCurrentInMa(OFString& value, const signed long pos = 0);
+
+        /** Get X-Ray Tube Current in mA
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1)
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getXRayTubeCurrentInMa(Float64& value, const unsigned long pos = 0);
+
+        /** Get Exposure in mAs
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getExposureInMas(OFString& value, const signed long pos = 0);
+
+        /** Get Exposure in mAs
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1)
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getExposureInMas(Float64& value, const unsigned long pos = 0);
+
+        /** Get Exposure Modulation Type
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getExposureModulationType(OFString& value, const signed long pos = 0);
+
+        /** Get Estimated Dose Saving
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getEstimatedDoseSaving(OFString& value, const signed long pos = 0);
+
+        /** Get Estimated Dose Saving
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1)
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getEstimatedDoseSaving(Float64& value, const unsigned long pos = 0);
+
+        /** Get CTDIvol
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getCTDIVol(OFString& value, const signed long pos = 0);
+
+        /** Get CTDIvol
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1)
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getCTDIVol(Float64& value, const unsigned long pos = 0);
+
+        virtual OFVector<CodeSequenceMacro*>& getCTDIPhantomTypeCodeSequence();
+
+        /** Get Water Equivalent Diameter
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getWaterEquivalentDiameter(OFString& value, const signed long pos = 0);
+
+        /** Get Water Equivalent Diameter
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1)
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getWaterEquivalentDiameter(Float64& value, const unsigned long pos = 0);
+
+        virtual OFVector<CodeSequenceMacro*>& getWaterEquivalentDiameterCalculationMethodCodeSequence();
+
+        /** Get Image And Fluoroscopy Area Dose Product
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getImageAndFluoroscopyAreaDoseProduct(OFString& value, const signed long pos = 0);
+
+        /** Get Image And Fluoroscopy Area Dose Product
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1)
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getImageAndFluoroscopyAreaDoseProduct(Float64& value, const unsigned long pos = 0);
+
+        // --- set() functionality ---
+
+        /** Set Referenced Path Index
+         *  @param  values Values that should be set
+         *  @param  checkValues If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setReferencedPathIndex(const OFVector<Uint16>& values, const OFBool checkValues = OFTrue);
+
+        /** Set Exposure Time in ms
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setExposureTimeInMs(const Float64 value, const OFBool checkValue = OFTrue);
+
+        /** Set X-Ray Tube Current In Ma
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setXRayTubeCurrentInMa(const Float64 value, const OFBool checkValue = OFTrue);
+
+        /** Set Exposure in mAs
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setExposureInMas(const Float64 value, const OFBool checkValue = OFTrue);
+
+        /** Set Exposure Modulation Type
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setExposureModulationType(const OFString& value, const OFBool checkValue = OFTrue);
+
+        /** Set Estimated Dose Saving
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setEstimatedDoseSaving(const Float64 value, const OFBool checkValue = OFTrue);
+
+        /** Set CTDIVol
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setCTDIVol(const Float64 value, const OFBool checkValue = OFTrue);
+
+        /** Set Water Equivalent Diameter
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setWaterEquivalentDiameter(const Float64 value, const OFBool checkValue = OFTrue);
+
+        /** Set Image and Fluoroscopy Area Dose Product
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setImageAndFluoroscopyAreaDoseProduct(const Float64 value,
+                                                                  const OFBool checkValue = OFTrue);
+
+    private:
+        /* Content of CT Exposure Macro item */
+
+        /// Referenced Path Index (US, VM 1-n, Required type 1C)
+        DcmUnsignedShort m_ReferencedPathIndex;
+
+        /// Exposure Time in ms (FD, 1, 1C)
+        DcmFloatingPointDouble m_ExposureTimeInMs;
+
+        /// X-Ray Tube Current in mA (FD, 1, 1C)
+        DcmFloatingPointDouble m_XRayTubeCurrentInMa;
+
+        /// Exposure in mAs (FD, 1, 1C)
+        DcmFloatingPointDouble m_ExposureInMas;
+
+        /// Exposure Modulation Type (CS, 1-n, 1C)
+        DcmCodeString m_ExposureModulationType;
+
+        /// Estimated Dose Saving (FD, 1, 2C)
+        DcmFloatingPointDouble m_EstimatedDoseSaving;
+
+        /// CTDIvol (FD, 1, 2C)
+        DcmFloatingPointDouble m_CTDIVol;
+
+        /// CTDI Phantom Type Code Sequence (SQ, 1, 3)
+        OFVector<CodeSequenceMacro*> m_CTDIPhantomTypeCodeSequence;
+
+        /// Water Equivalent Diameter (FD, 1, 3)
+        DcmFloatingPointDouble m_WaterEquivalentDiameter;
+
+        /// Water Equivalent Diameter Calculation Method Code Sequence (SQ, 1, 1C)
+        OFVector<CodeSequenceMacro*> m_WaterEquivalentDiameterCalculationMethodCodeSequence;
+
+        /// Image and Fluoroscopy Area Dose Product (DS, 1, 3)
+        DcmDecimalString m_ImageAndFluoroscopyAreaDoseProduct;
+    };
+
+    OFVector<FGCTExposureItem*>& getCTExposureItems();
+
+private:
+    /* Content of CT Exposure Macro */
+
+    /// Items of CT Exposure Macro
+    OFVector<FGCTExposureItem*> m_Items;
+};
+
+#endif // FGCTEXPOSURE_H
diff --git a/dcmfg/include/dcmtk/dcmfg/fgctgeometry.h b/dcmfg/include/dcmtk/dcmfg/fgctgeometry.h
new file mode 100644 (file)
index 0000000..d611553
--- /dev/null
@@ -0,0 +1,260 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT Geometry Functional Group
+ *
+ */
+
+#ifndef FGCTGEOMETRY_H
+#define FGCTGEOMETRY_H
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dctk.h"
+#include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/ofstd/ofstring.h"
+#include "dcmtk/ofstd/ofvector.h"
+
+/** Class representing the "CT Geometry" Functional Group Macro.
+ */
+class DCMTK_DCMFG_EXPORT FGCTGeometry : public FGBase
+{
+public:
+    /** Class representing the "CT Geometry" Functional Group Macro item
+     */
+    class DCMTK_DCMFG_EXPORT FGCTGeometryItem
+    {
+    public:
+        /** Constructor, creates empty functional group
+         */
+        FGCTGeometryItem();
+
+        /** Virtual destructor
+         */
+        virtual ~FGCTGeometryItem();
+
+        /** Returns a deep copy of this object
+         *  @return  Deep copy of this object
+         */
+        virtual FGCTGeometryItem* clone() const;
+
+        /** Clear all data
+         */
+        virtual void clearData();
+
+        /** Check whether the current content of this group is consistent and complete
+         *  @return EC_Normal, if no errors are found, error otherwise
+         */
+        virtual OFCondition check() const;
+
+        /** Read CT Geometry Sequence from given item
+         *  @param  item The item to read from
+         *  @return EC_Normal if reading was successful, error otherwise
+         */
+        virtual OFCondition read(DcmItem& item);
+
+        /** Writes the content of this class into given item
+         *  @param  item The item to write to
+         *  @return EC_Normal if writing was successful, error otherwise
+         */
+        virtual OFCondition write(DcmItem& item);
+
+        /** Comparison operator that compares the normalized value of this object
+         *  with a given object of the same type, i.e.\ the elements within both
+         *  functional groups (this and rhs parameter) are compared by value!
+         *  Both objects (this and rhs) need to have the same type (i.e.\ both
+         *  FGUnknown) to be comparable. This function is used in order
+         *  to decide whether a functional group already exists, or is new. This
+         *  is used in particular to find out whether a given functional group
+         *  can be shared (i.e.\ the same information already exists as shared
+         *  functional group) or is different from the same shared group. In that
+         *  case the shared functional group must be distributed into per-frame
+         *  functional groups, instead. The exact implementation for implementing
+         *  the comparison is not relevant. However, it must be a comparison
+         *  by value.
+         *  @param  rhs the right hand side of the comparison
+         *  @return 0 if the object values are equal.
+         *          -1 if either the value of the first component that does not match
+         *          is lower in the this object, or all compared components match
+         *          but this component is shorter. Also returned if this type and
+         *          rhs type (DcmFGTypes::E_FGType) do not match.
+         *          1 if either the value of the first component that does not match
+         *          is greater in this object, or all compared components match
+         *          but this component is longer.
+         */
+        virtual int compare(const FGCTGeometryItem& rhs) const;
+
+        // --- get() functionality ---
+
+        /** Get Referenced Path Index
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getReferencedPathIndex(OFString& value, const signed long pos = 0);
+
+        /** Get Referenced Path Index
+         *  @param  values Reference to variable that should hold the result
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getReferencedPathIndex(OFVector<Uint16>& values);
+
+        /** Get Distance Source to Detector
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getDistanceSourceToDetector(OFString& value, const signed long pos = 0);
+
+        /** Get Distance Source to Detector
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getDistanceSourceToDetector(Float64& value, const unsigned long pos = 0);
+
+        /** Get Distance Source to Data Collection Center
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getDistanceSourceToDataCollectionCenter(OFString& value, const signed long pos = 0);
+
+        /** Get Distance Source to Data Collection Center
+         *  @param  values Reference to variable that should hold the result
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getDistanceSourceToDataCollectionCenter(OFVector<Float64>& values);
+
+        // --- set() functionality ---
+
+        /** Set Referenced Path Index
+         *  @param  values Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setReferencedPathIndex(const OFVector<Uint16>& values, const OFBool checkValue = OFTrue);
+
+        /** Set Distance Source To Detector
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setDistanceSourceToDetector(const Float64 value, const OFBool checkValue = OFTrue);
+
+        /** Set Distance Source To Data Collection Center
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setDistanceSourceToDataCollectionCenter(const Float64 value,
+                                                                    const OFBool checkValue = OFTrue);
+
+    private:
+        /* Content of CT Geometry Macro */
+
+        /// Referenced Index Path (US, VM 1-n, Required type 1C)
+        DcmUnsignedShort m_ReferencedPathIndex;
+
+        /// Distance Source To Detector (DS, 1, 1C)
+        DcmDecimalString m_DistanceSourceToDetector;
+
+        /// Distance Source to Data Collection Center
+        DcmFloatingPointDouble m_DistanceSourceToDataCollectionCenter;
+    };
+
+    /** Constructor, creates empty functional group
+     */
+    FGCTGeometry();
+
+    /** Virtual destructor
+     */
+    virtual ~FGCTGeometry();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Returns shared functional group type
+     *  @return The functional group type (DcmFGTypes::EFGS_BOTH)
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clear all data
+     */
+    virtual void clearData();
+
+    /** Check whether the current content of this group is consistent and complete
+     *  @return EC_Normal, if no errors are found, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read CT Geometry Sequence from given item
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Writes the content of this class into CT Geometry Sequence
+     *  (newly created) into given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    OFVector<FGCTGeometryItem*>& getCTGeometryItems();
+
+private:
+    /* Content of CT Geometry Macro */
+
+    /// Items of this functional group macro
+    OFVector<FGCTGeometryItem*> m_Items;
+};
+
+#endif // FGCTGEOMETRY_H
diff --git a/dcmfg/include/dcmtk/dcmfg/fgctimageframetype.h b/dcmfg/include/dcmtk/dcmfg/fgctimageframetype.h
new file mode 100644 (file)
index 0000000..4344557
--- /dev/null
@@ -0,0 +1,257 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT Image Frame Type Functional Group
+ *
+ */
+
+#ifndef FGCTIMAGEFRAMETYPE_H
+#define FGCTIMAGEFRAMETYPE_H
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dctk.h"
+#include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/ofstd/ofstring.h"
+#include "dcmtk/ofstd/ofvector.h"
+
+/** Class representing the "CT Image Frame Type" Functional Group Macro. Can only be
+ *  used as per-frame functional group (never shared).
+ */
+class DCMTK_DCMFG_EXPORT FGCTImageFrameType : public FGBase
+{
+public:
+    static const OFString DT_VolBasedCalcTechnique_MaxIp;
+    static const OFString DT_VolBasedCalcTechnique_MinIp;
+    static const OFString DT_VolBasedCalcTechnique_VolumeRender;
+    static const OFString DT_VolBasedCalcTechnique_SurfaceRender;
+    static const OFString DT_VolBasedCalcTechnique_Mpr;
+    static const OFString DT_VolBasedCalcTechnique_CurvedMpr;
+    static const OFString DT_VolBasedCalcTechnique_None;
+    static const OFString DT_VolBasedCalcTechnique_Mixed;
+
+    enum E_PixelPresentation
+    {
+        E_PixelPres_Color,
+        E_PixelPres_Monochrome,
+        E_PixelPres_Mixed,
+        E_PixelPres_TrueColor,
+        E_PixelPres_Empty,
+        E_PixelPres_Invalid
+    };
+
+    enum E_VolumetricProperties
+    {
+        E_VolProp_Volume,
+        E_VolProp_Sampled,
+        E_VolProp_Distorted,
+        E_VolProp_Mixed,
+        E_VolProp_Empty,
+        E_VolProp_Invalid
+    };
+
+    /** Constructor, creates empty functional group
+     */
+    FGCTImageFrameType();
+
+    /** Virtual destructor
+     */
+    virtual ~FGCTImageFrameType();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Returns shared functional group type (always "per-frame")
+     *  @return The functional group type (DcmFGTypes::EFGS_BOTH)
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clear all data
+     */
+    virtual void clearData();
+
+    /** Check whether the current content of this group is consistent and complete
+     *  @return EC_Normal, if no errors are found, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read CT Image Frame Type Sequence from given item
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Writes the content of this class into CT Image Frame Type Sequence
+     *  (newly cerated) into given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    // --- get() functionality ---
+
+    /** Get Frame Type
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getFrameType(OFString& value, const signed long pos = 0);
+
+    /** Get Pixel Presentation
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getPixelPresentation(OFString& value, const signed long pos = 0);
+
+    /** Get Pixel Presentation
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Position of the value inside the DICOM element. If 0, the first
+     *          value is returned. If the no value at the given position exists,
+     *          an error is returned.
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getPixelPresentation(E_PixelPresentation& value, const signed long pos = 0);
+
+    /** Get Volumetric Properties
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getVolumetricProperties(OFString& value, const signed long pos = 0);
+
+    /** Get Volumetric Properties
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Position of the value inside the DICOM element. If 0, the first
+     *          value is returned. If the no value at the given position exists,
+     *          an error is returned.
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getVolumetricProperties(E_VolumetricProperties& value, const signed long pos = 0);
+
+    /** Get Volume Based Calculation Technique
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getVolumeBasedCalculationTechnique(OFString& value, const signed long pos = 0);
+
+    // --- set() functionality ---
+
+    /** Set Frame Type
+     *  @param  value Value that should be set
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setFrameType(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Pixel Presentation
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setPixelPresentation(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Pixel Presentation
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setPixelPresentation(const E_PixelPresentation& value, const OFBool checkValue = OFTrue);
+
+    /** Set Volumetric Properties
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setVolumetricProperties(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Volumetric Properties
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setVolumetricProperties(const E_VolumetricProperties& value, const OFBool checkValue = OFTrue);
+
+    /** Set Volume Based Calculation Technique
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setVolumeBasedCalculationTechnique(const OFString& value, const OFBool checkValue = OFTrue);
+
+    static E_PixelPresentation pixelPres2Enum(const OFString& str);
+
+    static OFBool pixelPres2Str(const E_PixelPresentation& eval, OFString& result);
+
+    static E_VolumetricProperties volProps2Enum(const OFString& str);
+
+    static OFBool volProps2Str(const E_VolumetricProperties& eval, OFString& result);
+
+private:
+    /* Content of CT Image Frame Type Macro */
+
+    /// Frame Type (CS, VM 4, Required type 1)
+    DcmCodeString m_FrameType;
+
+    /// Pixel Presentation (CS, 1, 1)
+    DcmCodeString m_PixelPresentation;
+
+    /// Volumetric Properties (CS, 1, 1)
+    DcmCodeString m_VolumetricProperties;
+
+    /// Volume Based Calculation Technique (CS, 1, 1)
+    DcmCodeString m_VolumeBasedCalculationTechnique;
+};
+
+#endif // FGCTIMAGEFRAMETYPE_H
diff --git a/dcmfg/include/dcmtk/dcmfg/fgctposition.h b/dcmfg/include/dcmtk/dcmfg/fgctposition.h
new file mode 100644 (file)
index 0000000..40d1b0f
--- /dev/null
@@ -0,0 +1,190 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT Position Functional Group
+ *
+ */
+
+#ifndef FGCTPOSITION_H
+#define FGCTPOSITION_H
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dctk.h"
+#include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/ofstd/ofstring.h"
+#include "dcmtk/ofstd/ofvector.h"
+
+/** Class representing the "CT Position" Functional Group Macro.
+ */
+class DCMTK_DCMFG_EXPORT FGCTPosition : public FGBase
+{
+public:
+    /** Constructor, creates empty functional group
+     */
+    FGCTPosition();
+
+    /** Virtual destructor
+     */
+    virtual ~FGCTPosition();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Returns shared functional group type
+     *  @return The functional group type (DcmFGTypes::EFGS_BOTH)
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clear all data
+     */
+    virtual void clearData();
+
+    /** Check whether the current content of this group is consistent and complete
+     *  @return EC_Normal, if no errors are found, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read CT Position Sequence from given item
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Writes the content of this class into CT Position Sequence
+     *  (newly created) into given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    // --- get() functionality ---
+
+    /** Get Table Speed
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getTablePosition(OFString& value, const signed long pos = 0);
+
+    /** Get Table Speed
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Position of the value inside the DICOM element. If 0, the first
+     *          value is returned. If the no value at the given position exists,
+     *          an error is returned.
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getTablePosition(Float64& value, const unsigned long pos = 0);
+
+    /** Get Data Collection Center (Patient)
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getDataCollectionCenterPatient(OFString& value, const signed long pos = 0);
+
+    /** Get Data Collection Center (Patient)
+     *  @param  values Reference to variable that should hold the result
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getDataCollectionCenterPatient(OFVector<Float64>& values);
+
+    /** Get Reconstruction Target Center (Patient)
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getReconstructionTargetCenterPatient(OFString& value, const signed long pos = 0);
+
+    /** Get Reconstruction Target Center (Patient)
+     *  @param  values Reference to variable that should hold the result
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getReconstructionTargetCenterPatient(OFVector<Float64>& values);
+
+    // --- set() functionality ---
+
+    /** Set Table Position
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setTablePosition(const Float64 value, const OFBool checkValue = OFTrue);
+
+    /** Set Data Collection Center (Patient)
+     *  @param  values Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setDataCollectionCenterPatient(const OFVector<Float64>& values,
+                                                       const OFBool checkValue = OFTrue);
+
+    /** Set Reconstruction Target Center (Patient)
+     *  @param  values Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setReconstructionTargetCenterPatient(const OFVector<Float64>& values,
+                                                             const OFBool checkValue = OFTrue);
+
+private:
+    /* Content of CT Position Macro */
+
+    /// Table Position (FD, VM 1, Required type 1C)
+    DcmFloatingPointDouble m_TablePosition;
+
+    /// Data Collection Center (Patient) (FD, 3, 1C)
+    DcmFloatingPointDouble m_DataCollectionCenterPatient;
+
+    /// Reconstruction Target Center (Patient) (FD, 3, 1C)
+    DcmFloatingPointDouble m_ReconstructionTargetCenterPatient;
+};
+
+#endif // FGCTPOSITION_H
diff --git a/dcmfg/include/dcmtk/dcmfg/fgctreconstruction.h b/dcmfg/include/dcmtk/dcmfg/fgctreconstruction.h
new file mode 100644 (file)
index 0000000..dff6d93
--- /dev/null
@@ -0,0 +1,286 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT Reconstruction Functional Group
+ *
+ */
+
+#ifndef FGCTRECONSTRUCTION_H
+#define FGCTRECONSTRUCTION_H
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dctk.h"
+#include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/ofstd/ofstring.h"
+#include "dcmtk/ofstd/ofvector.h"
+
+/** Class representing the "CT Reconstruction" Functional Group Macro.
+ */
+class DCMTK_DCMFG_EXPORT FGCTReconstruction : public FGBase
+{
+public:
+    /** Constructor, creates empty functional group
+     */
+    FGCTReconstruction();
+
+    /** Virtual destructor
+     */
+    virtual ~FGCTReconstruction();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Returns shared functional group type
+     *  @return The functional group type (DcmFGTypes::EFGS_BOTH)
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clear all data
+     */
+    virtual void clearData();
+
+    /** Check whether the current content of this group is consistent and complete
+     *  @return EC_Normal, if no errors are found, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read CT Reconstruction Sequence from given item
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Writes the content of this class into CT Reconstruction Sequence
+     *  (newly created) into given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    // --- get() functionality ---
+
+    /** Get Reconstruction Algorithm
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getReconstructionAlgorithm(OFString& value, const signed long pos = 0);
+
+    /** Get Convolution Kernel
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getConvolutionKernel(OFString& value, const signed long pos = 0);
+
+    /** Get Convolution Kernel Group
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getConvolutionKernelGroup(OFString& value, const signed long pos = 0);
+
+    /** Get Reconstruction Diameter
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getReconstructionDiameter(OFString& value, const signed long pos = 0);
+
+    /** Get Reconstruction Diameter
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getReconstructionDiameter(Float64& value, const unsigned long pos = 0);
+
+    /** Get Reconstruction Field of View
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getReconstructionFieldOfView(OFString& value, const signed long pos = 0);
+
+    /** Get Reconstruction Field of View
+     *  @param  values Reference to variable that should hold the result
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getReconstructionFieldOfView(OFVector<Float64>& values);
+
+    /** Get Reconstruction Pixel Spacing
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getReconstructionPixelSpacing(OFString& value, const signed long pos = 0);
+
+    /** Get Reconstruction Pixel Spacing
+     *  @param  values Reference to variable that should hold the result
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getReconstructionPixelSpacing(OFVector<Float64>& values);
+
+    /** Get Reconstruction Angle
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getReconstructionAngle(OFString& value, const signed long pos = 0);
+
+    /** Get Reconstruction Angle
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getReconstructionAngle(Float64& value, const unsigned long pos = 0);
+
+    /** Get Image Filter
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getImageFilter(OFString& value, const signed long pos = 0);
+
+    // --- set() functionality ---
+
+    /** Set Reconstruction Algorithm
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setReconstructionAlgorithm(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Convolution Kernel
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setConvolutionKernel(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Convolution Kernel Group
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setConvolutionKernelGroup(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Reconstruction Diameter
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setReconstructionDiameter(const Float64 value, const OFBool checkValue = OFTrue);
+
+    /** Set Reconstruction Field of View
+     *  @param  value1 First value that should be set
+     *  @param  value2 Second value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition
+    setReconstructionFieldOfView(const Float64 value1, const Float64 value2, const OFBool checkValue = OFTrue);
+
+    /** Set Reconstruction Pixel Spacing
+     *  @param  value1 First value that should be set
+     *  @param  value2 Second value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition
+    setReconstructionPixelSpacing(const Float64 value1, const Float64 value2, const OFBool checkValue = OFTrue);
+    /** Set Reconstruction Angle
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setReconstructionAngle(const Float64 value, const OFBool checkValue = OFTrue);
+
+    /** Set Image Filter
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setImageFilter(const OFString& value, const OFBool checkValue = OFTrue);
+
+private:
+    /* Content of CT Reconstruction Macro */
+
+    /// Reconstruction Algorithm (CS, VM 1, Required type 1C)
+    DcmCodeString m_ReconstructionAlgorithm;
+
+    /// Convolution Kernel (SH, 1-n, 1C)
+    DcmShortString m_ConvolutionKernel;
+
+    /// Convolution Kernel Group (CS, 1, 1C)
+    DcmCodeString m_ConvolutionKernelGroup;
+
+    /// Reconstruction Diameter (DS, 1, 1C)
+    DcmDecimalString m_ReconstructionDiameter;
+
+    /// Reconstruction Field of View (FD, 2, 1C)
+    DcmFloatingPointDouble m_ReconstructionFieldOfView;
+
+    /// Reconstruction Pixel Spacing (FD, 2, 1C)
+    DcmFloatingPointDouble m_ReconstructionPixelSpacing;
+
+    /// Reconstruction Angle (FD, 1, 1C)
+    DcmFloatingPointDouble m_ReconstructionAngle;
+
+    /// Image Filter (SH, 1, 1C)
+    DcmShortString m_ImageFilter;
+};
+
+#endif // FGCTRECONSTRUCTION_H
diff --git a/dcmfg/include/dcmtk/dcmfg/fgcttabledynamics.h b/dcmfg/include/dcmtk/dcmfg/fgcttabledynamics.h
new file mode 100644 (file)
index 0000000..2cc6caf
--- /dev/null
@@ -0,0 +1,267 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT Table Dynamics Functional Group
+ *
+ */
+
+#ifndef FGCTTABLEDYNAMICS_H
+#define FGCTTABLEDYNAMICS_H
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dctk.h"
+#include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/ofstd/ofstring.h"
+#include "dcmtk/ofstd/ofvector.h"
+
+/** Class representing the "CT Table Dynamics" Functional Group Macro.
+ */
+class DCMTK_DCMFG_EXPORT FGCTTableDynamics : public FGBase
+{
+
+public:
+    /** Class representing an item of the "CT Table Dynamics" Functional Group Macro.
+     */
+    class DCMTK_DCMFG_EXPORT FGCTTableDynamicsItem
+    {
+
+    public:
+        /** Constructor, creates empty functional group item
+         */
+        FGCTTableDynamicsItem();
+
+        /** Virtual destructor
+         */
+        virtual ~FGCTTableDynamicsItem();
+
+        /** Returns a deep copy of this object
+         *  @return  Deep copy of this object
+         */
+        virtual FGCTTableDynamicsItem* clone() const;
+
+        /** Clear all data
+         */
+        virtual void clearData();
+
+        /** Check whether the current content of this group item is consistent and complete
+         *  @return EC_Normal, if no errors are found, error otherwise
+         */
+        virtual OFCondition check() const;
+
+        /** Read CT Table Dynamics Sequence from given item
+         *  @param  item The item to read from
+         *  @return EC_Normal if reading was successful, error otherwise
+         */
+        virtual OFCondition read(DcmItem& item);
+
+        /** Writes the content of this class into given item
+         *  @param  item The item to write to
+         *  @return EC_Normal if writing was successful, error otherwise
+         */
+        virtual OFCondition write(DcmItem& item);
+
+        /** Comparison operator that compares the normalized value of this object
+         *  with a given object of the same type, i.e.\ the elements within both
+         *  functional groups (this and rhs parameter) are compared by value!
+         *  Both objects (this and rhs) need to have the same type (i.e.\ both
+         *  FGUnknown) to be comparable. This function is used in order
+         *  to decide whether a functional group already exists, or is new. This
+         *  is used in particular to find out whether a given functional group
+         *  can be shared (i.e.\ the same information already exists as shared
+         *  functional group) or is different from the same shared group. In that
+         *  case the shared functional group must be distributed into per-frame
+         *  functional groups, instead. The exact implementation for implementing
+         *  the comparison is not relevant. However, it must be a comparison
+         *  by value.
+         *  @param  rhs the right hand side of the comparison
+         *  @return 0 if the object values are equal.
+         *          -1 if either the value of the first component that does not match
+         *          is lower in the this object, or all compared components match
+         *          but this component is shorter. Also returned if this type and
+         *          rhs type (DcmFGTypes::E_FGType) do not match.
+         *          1 if either the value of the first component that does not match
+         *          is greater in this object, or all compared components match
+         *          but this component is longer.
+         */
+        virtual int compare(const FGCTTableDynamicsItem& rhs) const;
+
+        // --- get() functionality ---
+
+        /** Get Table Speed
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getTableSpeed(OFString& value, const signed long pos = 0);
+
+        /** Get Tube Angle
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Position of the value inside the DICOM element. If 0, the first
+         *          value is returned. If the no value at the given position exists,
+         *          an error is returned.
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getTableSpeed(Float64& value, const unsigned long pos = 0);
+
+        /** Get Table Feed per Rotation
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getTableFeedPerRotation(OFString& value, const signed long pos = 0);
+
+        /** Get Table Feed per Rotation
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Position of the value inside the DICOM element. If 0, the first
+         *          value is returned. If the no value at the given position exists,
+         *          an error is returned.
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getTableFeedPerRotation(Float64& value, const unsigned long pos = 0);
+
+        /** Get Spiral Pitch Factor
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getSpiralPitchFactor(OFString& value, const signed long pos = 0);
+
+        /** Get Spiral Pitch Factor
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Position of the value inside the DICOM element. If 0, the first
+         *          value is returned. If the no value at the given position exists,
+         *          an error is returned.
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getSpiralPitchFactor(Float64& value, const unsigned long pos = 0);
+
+        // --- set() functionality ---
+
+        /** Set Table Speed
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setTableSpeed(const Float64& value, const OFBool checkValue = OFTrue);
+
+        /** Set Table Feed per Rotation
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setTableFeedPerRotation(const Float64& value, const OFBool checkValue = OFTrue);
+
+        /** Set Spiral Pitch Factor
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setSpiralPitchFactor(const Float64& value, const OFBool checkValue = OFTrue);
+
+    private:
+        /* Content of CT Table Dynamics Macro (items) */
+
+        /// Acquisition Type (FD, VM 1, Required type 1C)
+        DcmFloatingPointDouble m_TableSpeed;
+
+        /// Table Feed Rotation (FD, 1, 1C)
+        DcmFloatingPointDouble m_TableFeedPerRotation;
+
+        /// Spiral Pitch Factor (FD, 1, 1C)
+        DcmFloatingPointDouble m_SpiralPitchFactor;
+    };
+
+    /** Constructor, creates empty functional group
+     */
+    FGCTTableDynamics();
+
+    /** Virtual destructor
+     */
+    virtual ~FGCTTableDynamics();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Returns shared functional group type
+     *  @return The functional group type (DcmFGTypes::EFGS_BOTH)
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clear all data
+     */
+    virtual void clearData();
+
+    /** Check whether the current content of this group is consistent and complete
+     *  @return EC_Normal, if no errors are found, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read CT Table Dynamics Sequence from given item
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Writes the content of this class into CT Table Dynamics Sequence
+     *  (newly created) into given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    OFVector<FGCTTableDynamicsItem*>& getCTTableDynamicsItems();
+
+private:
+    /// Items of this functional group macro
+    OFVector<FGCTTableDynamicsItem*> m_Items;
+};
+
+#endif // FGCTTABLEDYNAMICS_H
diff --git a/dcmfg/include/dcmtk/dcmfg/fgctxraydetails.h b/dcmfg/include/dcmtk/dcmfg/fgctxraydetails.h
new file mode 100644 (file)
index 0000000..557fb2e
--- /dev/null
@@ -0,0 +1,373 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT X-Ray Details Functional Group
+ *
+ */
+
+#ifndef FGCTXRAYDETAILS_H
+#define FGCTXRAYDETAILS_H
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dctk.h"
+#include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/ofstd/ofstring.h"
+#include "dcmtk/ofstd/ofvector.h"
+
+/** Class representing the "CT X-Ray Details" Functional Group Macro.
+ */
+class DCMTK_DCMFG_EXPORT FGCTXRayDetails : public FGBase
+{
+public:
+    /** Constructor, creates empty functional group
+     */
+    FGCTXRayDetails();
+
+    /** Virtual destructor
+     */
+    virtual ~FGCTXRayDetails();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Returns shared functional group type
+     *  @return The functional group type (DcmFGTypes::EFGS_BOTH)
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clear all data
+     */
+    virtual void clearData();
+
+    /** Check whether the current content of this group is consistent and complete
+     *  @return EC_Normal, if no errors are found, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read CT X-Ray Details Sequence from given item
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Writes the content of this class into CT X-Ray Details Sequence
+     *  (newly created) into given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    /** Class representing the "CT X-Ray Details" Functional Group Macro.
+     */
+    class DCMTK_DCMFG_EXPORT FGCTXRayDetailsItem
+    {
+    public:
+        /** Constructor, creates empty functional group
+         */
+        FGCTXRayDetailsItem();
+
+        /** Virtual destructor
+         */
+        virtual ~FGCTXRayDetailsItem();
+
+        /** Returns a deep copy of this object
+         *  @return  Deep copy of this object
+         */
+        virtual FGCTXRayDetailsItem* clone() const;
+
+        /** Clear all data
+         */
+        virtual void clearData();
+
+        /** Check whether the current content of this group is consistent and complete
+         *  @return EC_Normal, if no errors are found, error otherwise
+         */
+        virtual OFCondition check() const;
+
+        /** Read CT X-Ray Details Sequence item from given item
+         *  @param  item The item to read from
+         *  @return EC_Normal if reading was successful, error otherwise
+         */
+        virtual OFCondition read(DcmItem& item);
+
+        /** Writes the content of this class into CT X-Ray Details Sequence item
+         *  given item
+         *  @param  item The item to write to
+         *  @return EC_Normal if writing was successful, error otherwise
+         */
+        virtual OFCondition write(DcmItem& item);
+
+        /** Comparison operator that compares the normalized value of this object
+         *  with a given object of the same type, i.e.\ the elements within both
+         *  functional groups (this and rhs parameter) are compared by value!
+         *  Both objects (this and rhs) need to have the same type (i.e.\ both
+         *  FGUnknown) to be comparable. This function is used in order
+         *  to decide whether a functional group already exists, or is new. This
+         *  is used in particular to find out whether a given functional group
+         *  can be shared (i.e.\ the same information already exists as shared
+         *  functional group) or is different from the same shared group. In that
+         *  case the shared functional group must be distributed into per-frame
+         *  functional groups, instead. The exact implementation for implementing
+         *  the comparison is not relevant. However, it must be a comparison
+         *  by value.
+         *  @param  rhs the right hand side of the comparison
+         *  @return 0 if the object values are equal.
+         *          -1 if either the value of the first component that does not match
+         *          is lower in the this object, or all compared components match
+         *          but this component is shorter. Also returned if this type and
+         *          rhs type (DcmFGTypes::E_FGType) do not match.
+         *          1 if either the value of the first component that does not match
+         *          is greater in this object, or all compared components match
+         *          but this component is longer.
+         */
+        virtual int compare(const FGCTXRayDetailsItem& rhs) const;
+
+        // --- get() functionality ---
+
+        /** Get Referenced Path Index
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getReferencedPathIndex(OFString& value, const signed long pos = 0);
+
+        /** Get Referenced Path Index
+         *  @param  values Reference to variable that should hold the result
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getReferencedPathIndex(OFVector<Uint16>& values);
+
+        /** Get KVP
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getKVP(OFString& value, const signed long pos = 0);
+
+        /** Get KVP
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1)
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getKVP(Float64& value, const unsigned long pos = 0);
+
+        /** Get Focal Spots
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getFocalSpots(OFString& value, const signed long pos = 0);
+
+        /** Get Focal Spots
+         *  @param  values Reference to variable that should hold the result
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getFocalSpots(OFVector<Float64>& values);
+
+        /** Get Filter Type
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getFilterType(OFString& value, const signed long pos = 0);
+
+        /** Get Filter Material
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getFilterMaterial(OFString& value, const signed long pos = 0);
+
+        /** Get Calcium Scoring Mass Factor Patient
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getCalciumScoringMassFactorPatient(OFString& value, const signed long pos = 0);
+
+        /** Get Calcium Scoring Mass Factor Patient
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1)
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getCalciumScoringMassFactorPatient(Float32& value, const unsigned long pos = 0);
+
+        /** Get Calcium Scoring Mass Factor Device
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getCalciumScoringMassFactorDevice(OFString& value, const signed long pos = 0);
+
+        /** Get Calcium Scoring Mass Factor Device
+         *  @param  values Reference to variable that should hold the result
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getCalciumScoringMassFactorDevice(OFVector<Float64>& values);
+
+        /** Get Energy Weighting Factor
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getEnergyWeightingFactor(OFString& value, const signed long pos = 0);
+
+        /** Get Energy Weighting Factor
+         *  @param  value Reference to variable that should hold the result
+         *  @param  pos Index of the value to get (0..vm-1)
+         *  @return EC_Normal, if value could be returned, error otherwise
+         */
+        virtual OFCondition getEnergyWeightingFactor(Float32& value, const unsigned long pos = 0);
+
+        // --- set() functionality ---
+
+        /** Set Referenced Path Index
+         *  @param  values Values that should be set
+         *  @param  checkValues If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setReferencedPathIndex(const OFVector<Uint16>& values, const OFBool checkValues = OFTrue);
+
+        /** Set KVP
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setKVP(const Float64 value, const OFBool checkValue = OFTrue);
+
+        /** Set Focal Spots
+         *  @param  values Values that should be set
+         *  @param  checkValues If OFTrue, basic checks are performed whether the values are
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setFocalSpots(const OFVector<Float64>& values, const OFBool checkValues = OFTrue);
+
+        /** Set Filter Type
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setFilterType(const OFString& value, const OFBool checkValue = OFTrue);
+
+        /** Set Filter Material
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setFilterMaterial(const OFString& value, const OFBool checkValue = OFTrue);
+
+        /** Set Calcium Scoring Mass Factor Patient
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setCalciumScoringMassFactorPatient(const Float32 value, const OFBool checkValue = OFTrue);
+
+        /** Set Calcium Scoring Mass Factor Device
+         *  @param  values Values that should be set
+         *  @param  checkValues If OFTrue, basic checks are performed whether the values are
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setCalciumScoringMassFactorDevice(const OFVector<Float32>& values,
+                                                              const OFBool checkValues = OFTrue);
+
+        /** Set Energy Weighting Factor
+         *  @param  value Value that should be set
+         *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+         *          valid for this attribute
+         *  @return EC_Normal, if value was set, error otherwise
+         */
+        virtual OFCondition setEnergyWeightingFactor(const Float32 value, const OFBool checkValue = OFTrue);
+
+    private:
+        /* Content of CT X-Ray Details Macro */
+
+        /// Referenced Path Index (US, VM 1-n, Required type 1C)
+        DcmUnsignedShort m_ReferencedPathIndex;
+
+        /// KVP (DS, 1, 1C)
+        DcmDecimalString m_KVP;
+
+        /// Focal Spots (FD, 1-n, 1C)
+        DcmDecimalString m_FocalSpots;
+
+        /// Filter Type (SH, 1, 1C)
+        DcmShortString m_FilterType;
+
+        /// Filter Material (CS, 1-n, 1C)
+        DcmCodeString m_FilterMaterial;
+
+        /// Calcium Scoring Mass Factor Patient (FL, 1, 3)
+        DcmFloatingPointSingle m_CalciumScoringMassFactorPatient;
+
+        /// Calcium Scoring Mass Factor Device (FL, 3, 3)
+        DcmFloatingPointSingle m_CalciumScoringMassFactorDevice;
+
+        /// Energy Weighting Factor (FD, 1, 1C)
+        DcmFloatingPointSingle m_EnergyWeightingFactor;
+    };
+
+    // --- get() functionality ---
+
+    OFVector<FGCTXRayDetailsItem*>& getCTXRayDetailsItems();
+
+private:
+    /* Content of CT X-Ray Details Macro item */
+
+    /// Items of CT X-Ray Details macro
+    OFVector<FGCTXRayDetailsItem*> m_Items;
+};
+
+#endif // FGCTXRAYDETAILS_H
index 72e2371ad113a47d8d54ccf6c76f00ff774667e1..896dd70ac0af25660bdde1c7502ac710e423d24d 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-
 #ifndef FGDEFINE_H
 #define FGDEFINE_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofdefine.h"
 
+#include "dcmtk/ofstd/ofdefine.h"
 
 #ifdef dcmfg_EXPORTS
 #define DCMTK_DCMFG_EXPORT DCMTK_DECL_EXPORT
index 24b312ebfc924fc377d05def27c6e4c8107c57c7..6a3b79862d34f155c5ed4c4d5f6e68d690b94f56 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-
 #ifndef FGDERIMG_H
 #define FGDERIMG_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofvector.h"
-#include "dcmtk/ofstd/ofstring.h"
-#include "dcmtk/dcmiod/iodmacro.h"
+
 #include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/dcmiod/iodmacro.h"
+#include "dcmtk/ofstd/ofstring.h"
+#include "dcmtk/ofstd/ofvector.h"
 
 /** Class representing a single item of the Source Image Sequence
  */
@@ -35,269 +35,261 @@ class DCMTK_DCMFG_EXPORT SourceImageItem
 {
 
 public:
-
-  /** Constructor, constructs empty Source Image Sequence item
-   */
-  SourceImageItem();
-
-  /** Virtual destructor, cleans up memory
-   */
-  virtual ~SourceImageItem();
-
-  /** Clears all data handled by this component
-   */
-  virtual void clearData();
-
-  /** Check whether this item contains valid data
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  virtual OFCondition check() const;
-
-  /** Return handle to to purpose of reference code
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  virtual CodeSequenceMacro& getPurposeOfReferenceCode();
-
-  /** Returns handle to to image sop instance reference
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  virtual ImageSOPInstanceReferenceMacro& getImageSOPInstanceReference();
-
-  /** Reads source image item from given item
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& itemOfSourceImageSequence,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Writes source image item to given item
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& itemOfSourceImageSequence);
-
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGUnknown) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the this object, or all compared components match
-   *          but this component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in this object, or all compared components match
-   *          but this component is longer.
-   */
-  virtual int compare(const SourceImageItem& rhs) const;
-
-  /** Assignment operator, deletes old data
-   *  @param  rhs The item that should be assigned to "this" class
-   *  @return Reference to "this" class
-   */
-  SourceImageItem& operator=(const SourceImageItem& rhs);
+    /** Constructor, constructs empty Source Image Sequence item
+     */
+    SourceImageItem();
+
+    /** Virtual destructor, cleans up memory
+     */
+    virtual ~SourceImageItem();
+
+    /** Clears all data handled by this component
+     */
+    virtual void clearData();
+
+    /** Check whether this item contains valid data
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Return handle to to purpose of reference code
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual CodeSequenceMacro& getPurposeOfReferenceCode();
+
+    /** Returns handle to to image sop instance reference
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual ImageSOPInstanceReferenceMacro& getImageSOPInstanceReference();
+
+    /** Reads source image item from given item
+     *  @param  itemOfSourceImageSequence Reference to item of Source Image Sequence
+     *  @param  clearOldData If OFTue, old data in this class is cleared before reading
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& itemOfSourceImageSequence, const OFBool clearOldData = OFTrue);
+
+    /** Writes source image item to given item
+     *  @param  itemOfSourceImageSequence The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& itemOfSourceImageSequence);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const SourceImageItem& rhs) const;
+
+    /** Assignment operator, deletes old data
+     *  @param  rhs The item that should be assigned to "this" class
+     *  @return Reference to "this" class
+     */
+    SourceImageItem& operator=(const SourceImageItem& rhs);
 
 private:
+    /// Describes purpose of reference (single item of Purpose of Reference Code
+    /// Sequence)
+    CodeSequenceMacro m_PurposeOfReferenceCode;
 
-  /// Describes purpose of reference (single item of Purpose of Reference Code
-  /// Sequence)
-  CodeSequenceMacro m_PurposeOfReferenceCode;
-
-  /// Contains the referenced images (as represented by one of the items of
-  /// "this" Source Image Sequence)
-  ImageSOPInstanceReferenceMacro m_ImageSOPInstanceReference;
+    /// Contains the referenced images (as represented by one of the items of
+    /// "this" Source Image Sequence)
+    ImageSOPInstanceReferenceMacro m_ImageSOPInstanceReference;
 };
 
 /// Iterator for traversing over items of the Source Image Sequence
 typedef OFVector<SourceImageItem*>::iterator SourceImageIterator;
 
-
 /** Class representing a single item in Derivation Image Sequence
  */
 class DCMTK_DCMFG_EXPORT DerivationImageItem
 {
 public:
-
-  /** Constructor, initializes empty derivation image item
-   */
-  DerivationImageItem();
-
-  /** Virtual destructor
-   */
-  virtual ~DerivationImageItem();
-
-  /** Assignment operator, deletes old data
-   *  @param  rhs The item that should be assigned to "this" class
-   *  @return Reference to "this" class
-   */
-  DerivationImageItem& operator=(const DerivationImageItem& rhs);
-
-  /** Copy constructor, deletes old data
-   *  @param  rhs The item that should be used for initialization
-   */
-  DerivationImageItem(const DerivationImageItem& rhs);
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type
-   *  @param  rhs The right hand side of the comparison
-   *  @return 0 If the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the rhs object, or all compared components match
-   *          but the rhs component is shorter. Also returned if rhs cannot be
-   *          casted to DcmAttributeTag.
-   *          1 if either the value of the first component that does not match
-   *          is greater in the rhs object, or all compared components match
-   *          but the rhs component is longer.
-   */
-  virtual int compare(const DerivationImageItem& rhs) const;
-
-  /** Clears all data handled by this component
-   */
-  virtual void clearData();
-
-  /** Check whether item contains valid data
-   *  @return EC_Normal if item is valid, error otherwise
-   */
-  virtual OFCondition check() const;
-
-  /** Convenience function to add item representing reference to an object. No
-   *  restrictions are set which frames or segments from this image has been
-   *  actually used. However, such information could be added to the source
-   *  image item later by modifying the resulting item being handed back to the
-   *  caller.
-   *  @param  file Files that should be referenced by their UID, must be readable.
-   *  @param  purposeOfReference Code representing the purpose of reference
-   *          (Defined CID 7202)
-   *  @param  resultSourceImageItem The created derivation image item if
-   *          successful, NULL otherwise
-   *  @return EC_Normal if adding works, error code otherwise
-   */
-  virtual OFCondition addSourceImageItem(const OFString& file,
-                                         const CodeSequenceMacro& purposeOfReference,
-                                         SourceImageItem*& resultSourceImageItem);
-
-  /** Convenience function to add item representing reference to an object. No
-   *  restrictions are set which frames or segments from this image has been
-   *  actually used. However, such information could be added to the source
-   *  image item later by modifying the resulting item being handed back to the
-   *  caller.
-   *  @param  dataset DICOM dataset that should be referenced by their UID
-   *  @param  purposeOfReference Code representing the purpose of reference
-   *          (Defined CID 7202)
-   *  @param  resultSourceImageItem The created derivation image item if
-   *          successful, NULL otherwise
-   *  @return EC_Normal if adding works, error code otherwise
-   */
-  virtual OFCondition addSourceImageItem(DcmDataset *dataset,
-                                         const CodeSequenceMacro& purposeOfReference,
-                                         SourceImageItem*& resultSourceImageItem);
-
-  /** Convenience function to add items representing references to some objects
-   *  which all have the same purpose of reference (code). No restrictions are
-   *  set which frames or segments from those images have been actually used.
-   *  However, such information could be added to the source image item later by
-   *  modifying the resulting item handed back to the caller.
-   *  @param  files List of files that should be referenced by their UIDs.
-   *  @param  purposeOfReference Code representing the purpose of reference
-    *         (Defined CID 7202)
-   *  @param  resultSourceImageItems The created derivation image items (one per
-   *          file) if successful, NULL otherwise
-   *  @param  skipFileErrors If OFTrue, then files that could not be added will
-   *          not lead to error.
-   *  @return EC_Normal if adding works, error code otherwise
-   */
-  virtual OFCondition addSourceImageItems(const OFVector<OFString>& files,
-                                          const CodeSequenceMacro& purposeOfReference,
-                                          OFVector<SourceImageItem*>& resultSourceImageItems,
-                                          const OFBool skipFileErrors = OFFalse);
-
-  /** Convenience function to add items representing references to some objects
-   *  which all have the same purpose of reference (code). No restrictions are
-   *  set which frames or segments from those images have been actually used.
-   *  However, such information could be added to the source image item later by
-   *  modifying the resulting item handed back to the caller.
-   *  @param  datasets List of datasets that should be referenced by their UIDs.
-   *  @param  purposeOfReference Code representing the purpose of reference
-   *          (Defined CID 7202)
-   *  @param  resultSourceImageItems The created derivation image items (one per
-   *          file) if successful, NULL otherwise
-   *  @param  skipErrors If OFTrue, then files that could not be added will
-   *          not lead to error.
-   *  @return EC_Normal if adding works, error code otherwise
-   */
-  virtual OFCondition addSourceImageItems(const OFVector<DcmDataset*>& datasets,
-                                          const CodeSequenceMacro& purposeOfReference,
-                                          OFVector<SourceImageItem*>& resultSourceImageItems,
-                                          const OFBool skipErrors = OFFalse);
-
-   /** Get Derivation Description
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return status, EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getDerivationDescription(OFString &value,
-                                               const signed long pos = 0) const;
-
-  /** Get reference to derivation code items
-   *  @return Reference to derivation code items
-   */
-  virtual OFVector<CodeSequenceMacro*>& getDerivationCodeItems();
-
-  /** Get reference to source image items
-   *  @return Reference to source image items
-   */
-  virtual OFVector<SourceImageItem*>& getSourceImageItems();
-
-  /** Set Derivation Description
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setDerivationDescription(const OFString &value,
-                                               const OFBool checkValue = OFTrue);
-
-  /** Read Derivation Image Sequence Item describing derivation from a
-   *  set of images
-   *  @param  itemOfDerivationImageSequence The item to read from
-   *  @param  clearOldData If OFTrue, old data is deleted first
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& itemOfDerivationImageSequence,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write Derivation Image Sequence Item describing derivation from a
-   *  set of images
-   *  @param  itemOfDerivationImageSequence The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& itemOfDerivationImageSequence);
+    /** Constructor, initializes empty derivation image item
+     */
+    DerivationImageItem();
+
+    /** Virtual destructor
+     */
+    virtual ~DerivationImageItem();
+
+    /** Assignment operator, deletes old data
+     *  @param  rhs The item that should be assigned to "this" class
+     *  @return Reference to "this" class
+     */
+    DerivationImageItem& operator=(const DerivationImageItem& rhs);
+
+    /** Copy constructor, deletes old data
+     *  @param  rhs The item that should be used for initialization
+     */
+    DerivationImageItem(const DerivationImageItem& rhs);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type
+     *  @param  rhs The right hand side of the comparison
+     *  @return 0 If the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the rhs object, or all compared components match
+     *          but the rhs component is shorter. Also returned if rhs cannot be
+     *          casted to DcmAttributeTag.
+     *          1 if either the value of the first component that does not match
+     *          is greater in the rhs object, or all compared components match
+     *          but the rhs component is longer.
+     */
+    virtual int compare(const DerivationImageItem& rhs) const;
+
+    /** Clears all data handled by this component
+     */
+    virtual void clearData();
+
+    /** Check whether item contains valid data
+     *  @return EC_Normal if item is valid, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Convenience function to add item representing reference to an object. No
+     *  restrictions are set which frames or segments from this image has been
+     *  actually used. However, such information could be added to the source
+     *  image item later by modifying the resulting item being handed back to the
+     *  caller.
+     *  @param  file Files that should be referenced by their UID, must be readable.
+     *  @param  purposeOfReference Code representing the purpose of reference
+     *          (Defined CID 7202)
+     *  @param  resultSourceImageItem The created derivation image item if
+     *          successful, NULL otherwise
+     *  @return EC_Normal if adding works, error code otherwise
+     */
+    virtual OFCondition addSourceImageItem(const OFString& file,
+                                           const CodeSequenceMacro& purposeOfReference,
+                                           SourceImageItem*& resultSourceImageItem);
+
+    /** Convenience function to add item representing reference to an object. No
+     *  restrictions are set which frames or segments from this image has been
+     *  actually used. However, such information could be added to the source
+     *  image item later by modifying the resulting item being handed back to the
+     *  caller.
+     *  @param  dataset DICOM dataset that should be referenced by their UID
+     *  @param  purposeOfReference Code representing the purpose of reference
+     *          (Defined CID 7202)
+     *  @param  resultSourceImageItem The created derivation image item if
+     *          successful, NULL otherwise
+     *  @return EC_Normal if adding works, error code otherwise
+     */
+    virtual OFCondition addSourceImageItem(DcmDataset* dataset,
+                                           const CodeSequenceMacro& purposeOfReference,
+                                           SourceImageItem*& resultSourceImageItem);
+
+    /** Convenience function to add items representing references to some objects
+     *  which all have the same purpose of reference (code). No restrictions are
+     *  set which frames or segments from those images have been actually used.
+     *  However, such information could be added to the source image item later by
+     *  modifying the resulting item handed back to the caller.
+     *  @param  files List of files that should be referenced by their UIDs.
+     *  @param  purposeOfReference Code representing the purpose of reference
+     *         (Defined CID 7202)
+     *  @param  resultSourceImageItems The created derivation image items (one per
+     *          file) if successful, NULL otherwise
+     *  @param  skipFileErrors If OFTrue, then files that could not be added will
+     *          not lead to error.
+     *  @return EC_Normal if adding works, error code otherwise
+     */
+    virtual OFCondition addSourceImageItems(const OFVector<OFString>& files,
+                                            const CodeSequenceMacro& purposeOfReference,
+                                            OFVector<SourceImageItem*>& resultSourceImageItems,
+                                            const OFBool skipFileErrors = OFFalse);
+
+    /** Convenience function to add items representing references to some objects
+     *  which all have the same purpose of reference (code). No restrictions are
+     *  set which frames or segments from those images have been actually used.
+     *  However, such information could be added to the source image item later by
+     *  modifying the resulting item handed back to the caller.
+     *  @param  datasets List of datasets that should be referenced by their UIDs.
+     *  @param  purposeOfReference Code representing the purpose of reference
+     *          (Defined CID 7202)
+     *  @param  resultSourceImageItems The created derivation image items (one per
+     *          file) if successful, NULL otherwise
+     *  @param  skipErrors If OFTrue, then files that could not be added will
+     *          not lead to error.
+     *  @return EC_Normal if adding works, error code otherwise
+     */
+    virtual OFCondition addSourceImageItems(const OFVector<DcmDataset*>& datasets,
+                                            const CodeSequenceMacro& purposeOfReference,
+                                            OFVector<SourceImageItem*>& resultSourceImageItems,
+                                            const OFBool skipErrors = OFFalse);
+
+    /** Get Derivation Description
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getDerivationDescription(OFString& value, const signed long pos = 0) const;
+
+    /** Get reference to derivation code items
+     *  @return Reference to derivation code items
+     */
+    virtual OFVector<CodeSequenceMacro*>& getDerivationCodeItems();
+
+    /** Get reference to source image items
+     *  @return Reference to source image items
+     */
+    virtual OFVector<SourceImageItem*>& getSourceImageItems();
+
+    /** Set Derivation Description
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setDerivationDescription(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Read Derivation Image Sequence Item describing derivation from a
+     *  set of images
+     *  @param  itemOfDerivationImageSequence The item to read from
+     *  @param  clearOldData If OFTrue, old data is deleted first
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& itemOfDerivationImageSequence, const OFBool clearOldData = OFTrue);
+
+    /** Write Derivation Image Sequence Item describing derivation from a
+     *  set of images
+     *  @param  itemOfDerivationImageSequence The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& itemOfDerivationImageSequence);
 
 private:
+    // DICOM attributes.
+    // The comments for each attribute describe "Name: (VR, VM, Type)".
+    // See DICOM standard for further reference.
 
-  // DICOM attributes.
-  // The comments for each attribute describe "Name: (VR, VM, Type)".
-  // See DICOM standard for further reference.
-
-  /// Derivation Description: (ST, 1, 3)
-  DcmShortText m_DerivationDescription;
+    /// Derivation Description: (ST, 1, 3)
+    DcmShortText m_DerivationDescription;
 
-  /// List of derivation codes for this set of images (1-n items permitted)
-  OFVector<CodeSequenceMacro*> m_DerivationCodeItems;
-
-  // List of source images, as described by Source Image Sequence (0-n items
-  // permitted)
-  OFVector<SourceImageItem*> m_SourceImageItems;
+    /// List of derivation codes for this set of images (1-n items permitted)
+    OFVector<CodeSequenceMacro*> m_DerivationCodeItems;
 
+    // List of source images, as described by Source Image Sequence (0-n items
+    // permitted)
+    OFVector<SourceImageItem*> m_SourceImageItems;
 };
 
 /** Class representing the "Derivation Image Functional Group Macro"
@@ -305,110 +297,110 @@ private:
 class DCMTK_DCMFG_EXPORT FGDerivationImage : public FGBase
 {
 public:
-
-  /** Constructor creating an empty functional group
-   */
-  FGDerivationImage();
-
-  /** Virtual destructor, frees memory
-   */
-  virtual ~FGDerivationImage();
-
-  /** Returns a deep copy of this object
-   *  @return  Deep copy of this object
-   */
-  virtual FGBase *clone() const;
-
-  /** Convenience function to create a minimalistic FGDerivationImage
-   *  @param  derivationImages The list of SOP instances to reference
-   *  @param  derivationDescription Description of the derivation performed
-   *  @param  derivationCode Coded representation of the derivation description
-   *  @param  purposeOfReference Purpose of referencing the SOP instances
-   *  @return The created derivation image item, if successful, NULL otherwise
-   */
-  static FGDerivationImage* createMinimal(const OFVector<ImageSOPInstanceReferenceMacro>& derivationImages,
-                                          const OFString& derivationDescription,
-                                          const CodeSequenceMacro& derivationCode,
-                                          const CodeSequenceMacro& purposeOfReference);
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGDerivationImage) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the  first component that does not match
-   *          is lower in the rhs object, or all compared components match
-   *          but the rhs component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in the rhs object, or all compared components match
-   *          but the rhs component is longer.
-   */
-  virtual int compare(const FGBase& rhs) const;
-
-  /** Returns shared type of this functional group
-   *  @return Always returns DcmFGTypes::EFGS_BOTH
-   */
-  virtual DcmFGTypes::E_FGSharedType getSharedType() const {return DcmFGTypes::EFGS_BOTH;}
-
-  /** Convenience function to add an item only having a single derivation code
-    * derivation description. No source images have to provided but can be added
-    * later on the resulting DerivationImageItem.
-    * @param derivationCode Code describing derivation
-    * @param derivationDescription Free text description of derivation (can be
-    *        empty)
-    * @param item The created derivation image item if successful, NULL
-    *        otherwise
-    * @return EC_Normal if adding works, error code otherwise
-    */
-  virtual OFCondition addDerivationImageItem(const CodeSequenceMacro& derivationCode,
-                                             const OFString& derivationDescription,
-                                             DerivationImageItem*& item);
-
-  /** Clears all data handled by this component
-   */
-  virtual void clearData();
-
-  /** Checks whether this class contains valid data
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  virtual OFCondition check() const;
-
-  /** Get reference to derivation image items
-   *  @return Reference to derivation image items
-   */
-  virtual OFVector<DerivationImageItem*>& getDerivationImageItems();
-
-  /** Read Derivation Image Sequence from given item, which can contain zero or
-   *  more items
-   *  @param  item The item to read from
-   *  @return Returns EC_Normal if at least one derivation image item could be
-   *          read or no item exists at all, otherwise an error is returned
-   */
-  virtual OFCondition read(DcmItem& item);
-
-  /** Write Derivation Image Sequence (containing contain zero or more items)
-   *  to given item
-   *  @param  item The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
+    /** Constructor creating an empty functional group
+     */
+    FGDerivationImage();
+
+    /** Virtual destructor, frees memory
+     */
+    virtual ~FGDerivationImage();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Convenience function to create a minimalistic FGDerivationImage
+     *  @param  derivationImages The list of SOP instances to reference
+     *  @param  derivationDescription Description of the derivation performed
+     *  @param  derivationCode Coded representation of the derivation description
+     *  @param  purposeOfReference Purpose of referencing the SOP instances
+     *  @return The created derivation image item, if successful, NULL otherwise
+     */
+    static FGDerivationImage* createMinimal(const OFVector<ImageSOPInstanceReferenceMacro>& derivationImages,
+                                            const OFString& derivationDescription,
+                                            const CodeSequenceMacro& derivationCode,
+                                            const CodeSequenceMacro& purposeOfReference);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGDerivationImage) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the  first component that does not match
+     *          is lower in the rhs object, or all compared components match
+     *          but the rhs component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in the rhs object, or all compared components match
+     *          but the rhs component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    /** Returns shared type of this functional group
+     *  @return Always returns DcmFGTypes::EFGS_BOTH
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Convenience function to add an item only having a single derivation code
+     * derivation description. No source images have to provided but can be added
+     * later on the resulting DerivationImageItem.
+     * @param derivationCode Code describing derivation
+     * @param derivationDescription Free text description of derivation (can be
+     *        empty)
+     * @param item The created derivation image item if successful, NULL
+     *        otherwise
+     * @return EC_Normal if adding works, error code otherwise
+     */
+    virtual OFCondition addDerivationImageItem(const CodeSequenceMacro& derivationCode,
+                                               const OFString& derivationDescription,
+                                               DerivationImageItem*& item);
+
+    /** Clears all data handled by this component
+     */
+    virtual void clearData();
+
+    /** Checks whether this class contains valid data
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Get reference to derivation image items
+     *  @return Reference to derivation image items
+     */
+    virtual OFVector<DerivationImageItem*>& getDerivationImageItems();
+
+    /** Read Derivation Image Sequence from given item, which can contain zero or
+     *  more items
+     *  @param  item The item to read from
+     *  @return Returns EC_Normal if at least one derivation image item could be
+     *          read or no item exists at all, otherwise an error is returned
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Write Derivation Image Sequence (containing contain zero or more items)
+     *  to given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
 
 private:
-
-  /// List of derivation image items making up the Derivation Image Sequence
-  OFVector<DerivationImageItem*> m_DerivationImageItems;
-
+    /// List of derivation image items making up the Derivation Image Sequence
+    OFVector<DerivationImageItem*> m_DerivationImageItems;
 };
 
 #endif // FGDERIMG_H
index c44de47069c0957228b1df7c31d05f2bcea3a585..72ce723f07d1d9b9ba4250c06e0927e460394104 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define FGFACT_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofmap.h"
+
 #include "dcmtk/dcmdata/dctagkey.h"
 #include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/ofstd/ofmap.h"
 
 class FGBase;
 
-
 /** Singleton class that is used to create functional groups by knowing
  *  their type or other unique features, i.e.\ offering factory functionality.
  */
 class DCMTK_DCMFG_EXPORT FGFactory
 {
 public:
-
-  /** Return the single instance of the factory
-   *  @return The instance of FGFactory
-   */
-  static FGFactory& instance();
-
-  /** Create new functional group based on given type
-   *  @param fgtype The type of functional group to create
-   *  @return The functional group or NULL if error occurs
-   */
-  FGBase *create(const DcmFGTypes::E_FGType fgtype);
-
-  /** Create new functional group based its unique sequence tag key
-   *  @param fgSequenceKey Tag key of the functional groups sequence
-   *  @return The functional group or NULL if error occurs
-   */
-  FGBase *create(const DcmTagKey& fgSequenceKey);
+    /** Return the single instance of the factory
+     *  @return The instance of FGFactory
+     */
+    static FGFactory& instance();
+
+    /** Create new functional group based on given type
+     *  @param fgtype The type of functional group to create
+     *  @return The functional group or NULL if error occurs
+     */
+    FGBase* create(const DcmFGTypes::E_FGType fgtype);
+
+    /** Create new functional group based its unique sequence tag key
+     *  @param fgSequenceKey Tag key of the functional groups sequence
+     *  @return The functional group or NULL if error occurs
+     */
+    FGBase* create(const DcmTagKey& fgSequenceKey);
 
 private:
-
-  /** Private undefined constructor (singleton implementation)
-   */
-  FGFactory();
-
-  /** Private undefined copy constructor (singleton implementation)
-   */
-  FGFactory(const FGFactory&);
-
-  /** Private undefined assignment operator (singleton implementation)
-   */
-  FGFactory& operator=(const FGFactory&);
-
-  /** Private undefined destructor (singleton implementation)
-   */
-  ~FGFactory() {}
-
-  /// The instance of FGFactory handled by this singleton class
-  static FGFactory* m_Instance;
-
+    /** Private undefined constructor (singleton implementation)
+     */
+    FGFactory();
+
+    /** Private undefined copy constructor (singleton implementation)
+     */
+    FGFactory(const FGFactory&);
+
+    /** Private undefined assignment operator (singleton implementation)
+     *  @param  rhs Right hand side of assignment
+     *  @return Reference to this class
+     */
+    FGFactory& operator=(const FGFactory& rhs);
+
+    /** Private undefined destructor (singleton implementation)
+     */
+    ~FGFactory()
+    {
+    }
+
+    /// The instance of FGFactory handled by this singleton class
+    static FGFactory* m_Instance;
 };
 
 #endif // FGFACT_H
index 2aea9849a6458a985ed6734a5bccfc048b7c1929..1cc3f688eb8658af597f4842c24cc3e8f19654aa 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define FGFRACON_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofvector.h"
-#include "dcmtk/ofstd/ofstring.h"
+
 #include "dcmtk/dcmdata/dctk.h"
 #include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/ofstd/ofstring.h"
+#include "dcmtk/ofstd/ofvector.h"
 
 /** Class representing the "Frame Content" Functional Group Macro. Can only be
  *  used as per-frame functional group (never shared).
 class DCMTK_DCMFG_EXPORT FGFrameContent : public FGBase
 {
 public:
-
-  /** Constructor, creates empty functional group
-   */
-  FGFrameContent();
-
-  /** Virtual destructor
-   */
-  virtual ~FGFrameContent();
-
-  /** Returns a deep copy of this object
-   *  @return  Deep copy of this object
-   */
-  virtual FGBase *clone() const;
-
-  /** Returns shared functional group type (always "per-frame")
-   *  @return The functional group type (DcmFGTypes::EFGS_ONLYPERFRAME)
-   */
-  virtual DcmFGTypes::E_FGSharedType getSharedType() const {return DcmFGTypes::EFGS_ONLYPERFRAME;}
-
-  /** Clear all data
-   */
-  virtual void clearData();
-
-  /** Check whether the current content of this group is consistent and complete
-   *  @return EC_Normal, if no errors are found, error otherwise
-   */
-  virtual OFCondition check() const;
-
-  /** Read Frame Content Sequence from given item
-   *  @param  item The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& item);
-
-  /** Writes the content of this class into Frame Content Sequence
-   *  (newly cerated) into given item
-   *  @param  item The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGUnknown) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the this object, or all compared components match
-   *          but this component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in this object, or all compared components match
-   *          but this component is longer.
-   */
-  virtual int compare(const FGBase& rhs) const;
-
-  // --- get() functionality ---
-
-  /** Get Frame Acquisition Number
-   *  @param  value Reference to variable that should hold the result
-   *  @param  pos Position of the value inside the DICOM element. If 0, the first
-   *          value is returned. If the no value at the given position exists,
-   *          an error is returned.
-   *  @return EC_Normal, if value could be returned, error otherwise
-   */
-  virtual OFCondition getFrameAcquisitionNumber(Uint16& value,
-                                                const signed long pos = 0);
-
-  /** Get Frame Reference Date Time
-   *  @param  value Reference to variable that should hold the result
-   *  @param  pos Position of the value inside the DICOM element. If 0, the first
-   *          value is returned. If the no value at the given position exists,
-   *          an error is returned.
-   *  @return EC_Normal, if value could be returned, error otherwise
-   */
-  virtual OFCondition getFrameReferenceDateTime(OFString& value,
-                                                const signed long pos = 0);
-  /** Get Frame Acquisition Date Time
-   *  @param  value Reference to variable that should hold the result
-   *  @param  pos Position of the value inside the DICOM element. If 0, the first
-   *          value is returned. If the no value at the given position exists,
-   *          an error is returned.
-   *  @return EC_Normal, if value could be returned, error otherwise
-   */
-  virtual OFCondition getFrameAcquisitionDateTime(OFString& value,
-                                                  const signed long pos = 0);
-
-  /** Get Frame Acquisition Duration
-   *  @param  value Reference to variable that should hold the result
-   *  @param  pos Position of the value inside the DICOM element. If 0, the first
-   *          value is returned. If the no value at the given position exists,
-   *           an error is returned.
-   *  @return EC_Normal, if value could be returned, error otherwise
-   */
-  virtual OFCondition getFrameAcquisitionDuration(Float64& value,
-                                                  const unsigned long pos = 0);
-
-  /** Get Cardiac Cycle Position
-   *  @param  value Reference to variable that should hold the result
-   *  @param  pos Position of the value inside the DICOM element. If 0, the first
-   *          value is returned. If the no value at the given position exists,
-   *          an error is returned.
-   *  @return EC_Normal, if value could be returned, error otherwise
-   */
-  virtual OFCondition getCardiacCyclePosition(OFString& value,
-                                              const signed long pos = 0);
-
-  /** Get Respiratory Cycle Position
-   *  @param  value Reference to variable that should hold the result
-   *  @param  pos Position of the value inside the DICOM element. If 0, the first
-   *          value is returned. If the no value at the given position exists,
-   *          an error is returned.
-   *  @return EC_Normal, if value could be returned, error otherwise
-   */
-  virtual OFCondition getRespiratoryCyclePosition(OFString& value,
-                                                  const signed long pos = 0);
-
-  /** Get Dimension Index Value
-   *  @param  value Reference to variable that should hold the result
-   *  @param  pos Position of the value inside the DICOM element. If 0, the first
-   *          value is returned. If the no value at the given position exists,
-   *          an error is returned.
-   *  @return EC_Normal, if value could be returned, error otherwise
-   */
-  virtual OFCondition getDimensionIndexValues(Uint32& value,
-                                              const signed long pos = 0);
-
-  /** Get Temporal Position Index
-   *  @param  value Reference to variable that should hold the result
-   *  @param  pos Position of the value inside the DICOM element. If 0, the first
-   *          value is returned. If the no value at the given position exists,
-   *          an error is returned.
-   *  @return EC_Normal, if value could be returned, error otherwise
-   */
-  virtual OFCondition getTemporalPositionIndex(Uint32& value,
-                                               const signed long pos = 0);
-
-  /** Get Stack ID
-   *  @param  value Reference to variable that should hold the result
-   *  @param  pos Position of the value inside the DICOM element. If 0, the first
-   *          value is returned. If the no value at the given position exists,
-   *          an error is returned.
-   *  @return EC_Normal, if value could be returned, error otherwise
-   */
-  virtual OFCondition getStackID(OFString& value,
-                                 const signed long pos = 0);
-
-  /** Get In-Stack Position Number
-   *  @param  value Reference to variable that should hold the result
-   *  @param  pos Position of the value inside the DICOM element. If 0, the first
-   *          value is returned. If the no value at the given position exists,
-   *          an error is returned.
-   *  @return EC_Normal, if value could be returned, error otherwise
-   */
-  virtual OFCondition getInStackPositionNumber(Uint32& value,
-                                               const signed long pos = 0);
-
-  /** Get Frame Comments
-   *  @param  value Reference to variable that should hold the result
-   *  @param  pos Position of the value inside the DICOM element. If 0, the first
-   *          value is returned. If the no value at the given position exists,
-   *          an error is returned.
-   *  @return EC_Normal, if value could be returned, error otherwise
-   */
-  virtual OFCondition getFrameComments(OFString& value,
-                                       const signed long pos = 0);
-
-  /** Get Frame Label
-   *  @param  value Reference to variable that should hold the result
-   *  @param  pos Position of the value inside the DICOM element. If 0, the first
-   *          value is returned. If the no value at the given position exists,
-   *          an error is returned.
-   *  @return EC_Normal, if value could be returned, error otherwise
-   */
-  virtual OFCondition getFrameLabel(OFString& value,
-                                    const signed long pos = 0);
-
-  // --- set() functionality ---
-
-  /** Set Frame Acquisition Number
-   *  @param  value Value that should be set
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal, if value was set, error otherwise
-   */
-  virtual OFCondition setFrameAcquisitionNumber(const Uint16& value,
-                                                const OFBool checkValue = OFTrue);
-
-  /** Set Frame Frame Reference Date Time
-   *  @param  value Value that should be set
-   *  @param  checkValue If OFTrue, basic checks are performed whether the value is
-   *          valid for this attribute
-   *  @return EC_Normal, if value was set, error otherwise
-   */
-  virtual OFCondition setFrameReferenceDateTime(const OFString& value,
-                                                const OFBool checkValue = OFTrue);
-
-  /** Set Frame Acquisition Date Time
-   *  @param  value Value that should be set
-   *  @param  checkValue If OFTrue, basic checks are performed whether the value is
-   *          valid for this attribute
-   *  @return EC_Normal, if value was set, error otherwise
-   */
-  virtual OFCondition setFrameAcquisitionDateTime(const OFString& value,
-                                                  const OFBool checkValue = OFTrue);
-
-  /** Set Frame Acquisition Duration
-   *  @param  value Value that should be set
-   *  @param  checkValue If OFTrue, basic checks are performed whether the value is
-   *          valid for this attribute
-   *  @return EC_Normal, if value was set, error otherwise
-   */
-  virtual OFCondition setFrameAcquisitionDuration(const Float64& value,
-                                                  const OFBool checkValue = OFTrue);
-
-  /** Set Cardiac Cycle Position
-   *  @param  value Value that should be set
-   *  @param  checkValue If OFTrue, basic checks are performed whether the value is
-   *          valid for this attribute
-   *  @return EC_Normal, if value was set, error otherwise
-   */
-  virtual OFCondition setCardiacCyclePosition(const OFString& value,
-                                              const OFBool checkValue = OFTrue);
-
-  /** Set Respiratory Cycle Position
-   *  @param  value Value that should be set
-   *  @param  checkValue If OFTrue, basic checks are performed whether the value is
-   *          valid for this attribute
-   *  @return EC_Normal, if value was set, error otherwise
-   */
-  virtual OFCondition setRespiratoryCyclePosition(const OFString& value,
-                                                  const OFBool checkValue = OFTrue);
-
-  /** Set one of the Dimension Index Values
-   *  @param  value Value that should be set (lowest index starts with 1)
-   *  @param  dim The position of the value that should be set (lowest index
-   *          starts with 0), i.e.\ select the 1st, 2nd, ..nth dimension
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal, if value was set, error otherwise
-   */
-  virtual OFCondition setDimensionIndexValues(const Uint32& value,
-                                              const unsigned int dim,
-                                              const OFBool checkValue = OFTrue);
-
-  /** Set Temporal Position Index
-   *  @param  value Value that should be set
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal, if value was set, error otherwise
-   */
-  virtual OFCondition setTemporalPositionIndex(const Uint32& value,
-                                               const OFBool checkValue = OFTrue);
-
-  /** Set Stack ID
-   *  @param  value Value that should be set
-   *  @param  checkValue If OFTrue, basic checks are performed whether the value is
-   *          valid for this attribute
-   *  @return EC_Normal, if value was set, error otherwise
-   */
-  virtual OFCondition setStackID(const OFString& value,
-                                 const OFBool checkValue = OFTrue);
-
-  /** Set In-Stack Position Number
-   *  @param  value Value that should be set
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal, if value was set, error otherwise
-   */
-  virtual OFCondition setInStackPositionNumber(const Uint32& value,
-                                               const OFBool checkValue = OFTrue);
-
-  /** Set Frame Comments
-   *  @param  value Value that should be set
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal, if value was set, error otherwise
-   */
-  virtual OFCondition setFrameComments(const OFString& value,
-                                       const OFBool checkValue = OFTrue);
-
-  /** Set Frame Label
-   *  @param  value Value that should be set
-   *  @param  checkValue If OFTrue, basic checks are performed whether the value is
-   *          valid for this attribute
-   *  @return EC_Normal, if value was set, error otherwise
-   */
-  virtual OFCondition setFrameLabel(const OFString& value,
-                                    const OFBool checkValue = OFTrue);
+    /** Constructor, creates empty functional group
+     */
+    FGFrameContent();
+
+    /** Virtual destructor
+     */
+    virtual ~FGFrameContent();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Returns shared functional group type (always "per-frame")
+     *  @return The functional group type (DcmFGTypes::EFGS_ONLYPERFRAME)
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_ONLYPERFRAME;
+    }
+
+    /** Clear all data
+     */
+    virtual void clearData();
+
+    /** Check whether the current content of this group is consistent and complete
+     *  @return EC_Normal, if no errors are found, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read Frame Content Sequence from given item
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Writes the content of this class into Frame Content Sequence
+     *  (newly cerated) into given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    // --- get() functionality ---
+
+    /** Get Frame Acquisition Number
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Position of the value inside the DICOM element. If 0, the first
+     *          value is returned. If the no value at the given position exists,
+     *          an error is returned.
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getFrameAcquisitionNumber(Uint16& value, const unsigned long pos = 0);
+
+    /** Get Frame Reference Date Time
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getFrameReferenceDateTime(OFString& value, const signed long pos = 0);
+    /** Get Frame Acquisition Date Time
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getFrameAcquisitionDateTime(OFString& value, const signed long pos = 0);
+
+    /** Get Frame Acquisition Duration
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Position of the value inside the DICOM element. If 0, the first
+     *          value is returned. If the no value at the given position exists,
+     *           an error is returned.
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getFrameAcquisitionDuration(Float64& value, const unsigned long pos = 0);
+
+    /** Get Cardiac Cycle Position
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getCardiacCyclePosition(OFString& value, const signed long pos = 0);
+
+    /** Get Respiratory Cycle Position
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getRespiratoryCyclePosition(OFString& value, const signed long pos = 0);
+
+    /** Get Dimension Index Value
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Position of the value inside the DICOM element. If 0, the first
+     *          value is returned. If the no value at the given position exists,
+     *          an error is returned.
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getDimensionIndexValues(Uint32& value, const unsigned long pos = 0);
+
+    /** Get Temporal Position Index
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Position of the value inside the DICOM element. If 0, the first
+     *          value is returned. If the no value at the given position exists,
+     *          an error is returned.
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getTemporalPositionIndex(Uint32& value, const unsigned long pos = 0);
+
+    /** Get Stack ID
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getStackID(OFString& value, const signed long pos = 0);
+
+    /** Get In-Stack Position Number
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getInStackPositionNumber(Uint32& value, const unsigned long pos = 0);
+
+    /** Get Frame Comments
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getFrameComments(OFString& value, const signed long pos = 0);
+
+    /** Get Frame Label
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getFrameLabel(OFString& value, const signed long pos = 0);
+
+    // --- set() functionality ---
+
+    /** Set Frame Acquisition Number
+     *  @param  value Value that should be set
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setFrameAcquisitionNumber(const Uint16& value, const OFBool checkValue = OFTrue);
+
+    /** Set Frame Frame Reference Date Time
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setFrameReferenceDateTime(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Frame Acquisition Date Time
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setFrameAcquisitionDateTime(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Frame Acquisition Duration
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setFrameAcquisitionDuration(const Float64& value, const OFBool checkValue = OFTrue);
+
+    /** Set Cardiac Cycle Position
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setCardiacCyclePosition(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Respiratory Cycle Position
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setRespiratoryCyclePosition(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set one of the Dimension Index Values
+     *  @param  value Value that should be set (lowest index starts with 1)
+     *  @param  dim The position of the value that should be set (lowest index
+     *          starts with 0), i.e.\ select the 1st, 2nd, ..nth dimension
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition
+    setDimensionIndexValues(const Uint32& value, const unsigned int dim, const OFBool checkValue = OFTrue);
+
+    /** Set Temporal Position Index
+     *  @param  value Value that should be set
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setTemporalPositionIndex(const Uint32& value, const OFBool checkValue = OFTrue);
+
+    /** Set Stack ID
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setStackID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set In-Stack Position Number
+     *  @param  value Value that should be set
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setInStackPositionNumber(const Uint32& value, const OFBool checkValue = OFTrue);
+
+    /** Set Frame Comments
+     *  @param  value Value that should be set
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setFrameComments(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Frame Label
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setFrameLabel(const OFString& value, const OFBool checkValue = OFTrue);
 
 private:
+    /* Content of Frame Content Macro */
 
-  /* Content of Frame Content Macro */
-
-  /// Frame Acquisition Number (US, VM 1, Required type 3)
-  DcmUnsignedShort m_FrameAcquisitonNumber;
+    /// Frame Acquisition Number (US, VM 1, Required type 3)
+    DcmUnsignedShort m_FrameAcquisitonNumber;
 
-  /// Frame Reference DateTime (DT, 1, 1C)
-  DcmDateTime m_FrameReferenceDateTime;
+    /// Frame Reference DateTime (DT, 1, 1C)
+    DcmDateTime m_FrameReferenceDateTime;
 
-  /// Frame Acquisition DateTime (DT, 1, 1C)
-  DcmDateTime m_FrameAcquisitionDateTime;
+    /// Frame Acquisition DateTime (DT, 1, 1C)
+    DcmDateTime m_FrameAcquisitionDateTime;
 
-  /// Frame Acquisition Duration (FD, 1, 1C)
-  DcmFloatingPointDouble m_FrameAcquisitionDuration;
+    /// Frame Acquisition Duration (FD, 1, 1C)
+    DcmFloatingPointDouble m_FrameAcquisitionDuration;
 
-  /// Cardiac Cycle Position (CS, 1, 3)
-  DcmCodeString m_CardiacCyclePosition;
+    /// Cardiac Cycle Position (CS, 1, 3)
+    DcmCodeString m_CardiacCyclePosition;
 
-  /// Respiratory Cycle Position (CS, 1, 3)
-  DcmCodeString m_RespiratoryCyclePosition;
+    /// Respiratory Cycle Position (CS, 1, 3)
+    DcmCodeString m_RespiratoryCyclePosition;
 
-  /// Dimension Index Values (UL, 1-n, 1C)
-  DcmUnsignedLong m_DimensionIndexValues;
+    /// Dimension Index Values (UL, 1-n, 1C)
+    DcmUnsignedLong m_DimensionIndexValues;
 
-  /// Temporal Position Index (UL, 1, 1C)
-  DcmUnsignedLong m_TemporalPositionIndex;
+    /// Temporal Position Index (UL, 1, 1C)
+    DcmUnsignedLong m_TemporalPositionIndex;
 
-  /// Stack ID (SH, 1, 1C)
-  DcmShortString m_StackID;
+    /// Stack ID (SH, 1, 1C)
+    DcmShortString m_StackID;
 
-  /// In-Stack Position Number (UL, 1, 1C)
-  DcmUnsignedLong m_InStackPositionNumber;
+    /// In-Stack Position Number (UL, 1, 1C)
+    DcmUnsignedLong m_InStackPositionNumber;
 
-  /// Frame Comments (LT, 1, 3)
-  DcmLongText m_FrameComments;
+    /// Frame Comments (LT, 1, 3)
+    DcmLongText m_FrameComments;
 
-  /// Frame Label (LO, 1, 3)
-  DcmLongString m_FrameLabel;
+    /// Frame Label (LO, 1, 3)
+    DcmLongString m_FrameLabel;
 };
 
 #endif // FGFRACON_H
index c29a78e95623b280ec04fd04904603a626b33d39..c3af3c52f6931a5cba0ff6507930e1aa475d2a7f 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define FGFRAMEANATOMY_H
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcitem.h"
-#include "dcmtk/dcmiod/iodmacro.h"
 #include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/dcmiod/iodmacro.h"
 
 /** Class representing the Frame Anatomy Functional Group Macro
  */
 class DCMTK_DCMFG_EXPORT FGFrameAnatomy : public FGBase
 {
 public:
-
-  /** Enumerated values for attribute "Laterality"
-   */
-  enum LATERALITY
-  {
-    /// Undefined (e.g.\ value not set)
-    LATERALITY_UNDEFINED,
-    /// Invalid Laterality, e.g. when invalid value is read from file
-    LATERALITY_INVALID,
-    /// Right body part
-    LATERALITY_R,
-    /// Left body part
-    LATERALITY_L,
-    /// Unpaired body part
-    LATERALITY_UNPAIRED,
-    /// Both, left and right
-    LATERALITY_BOTH
-  };
-
-  /** Constructor, creates empty Frame Anatomy Functional Group
-   */
-  FGFrameAnatomy();
-
-  /** Virtual destructor, frees memory
-   */
-  virtual ~FGFrameAnatomy();
-
-  /** Returns a deep copy of this object
-   *  @return Deep copy of this object
-   */
-  virtual FGBase *clone() const;
-
-  /** Returns shared type of this group (can be shared or per-frame)
-   *  @return Always returns DcmFGTypes::EFGS_BOTH;
-   */
-  virtual DcmFGTypes::E_FGSharedType getSharedType() const {return DcmFGTypes::EFGS_BOTH;}
-
-  /** Clear all data
-   */
-  virtual void clearData();
-
-  /** Check whether data in functional group is valid
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  virtual OFCondition check() const;
-
-  /** Read functional group from given item
-   *  @param  item The item to read from, must contain Frame Anatomy Sequence
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& item);
-
-  /** Write functional group to given item
-   *  @param  item The item to write Frame Anatomy Sequence to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
-
-  // --- get() functionality ---
-
-  /** Get Laterality
-   *  @param  value Reference to variable in which the value should be stored
-   *  @return EC_Normal if successful, an error code otherwise (i.e. if
-   *          value is LATERALITY_INVALID).
-   */
-  virtual OFCondition getLaterality(LATERALITY& value);
-
-  /** Get anatomy information
-   *  @return Reference to anatomic information
-   */
-  virtual GeneralAnatomyMacro& getAnatomy();
-
-  // --- set() functionality ---
-
-  /** Set Laterality
-   *  @param  value Value to be set
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setLaterality(const LATERALITY& value);
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGUnknown) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the this object, or all compared components match
-   *          but this component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in this object, or all compared components match
-   *          but this component is longer.
-   */
-  virtual int compare(const FGBase& rhs) const;
-
-  static LATERALITY str2Laterality(const OFString& lat);
-
-  static OFString laterality2Str(const LATERALITY lat);
-
-  static OFBool isLateralityValid(const LATERALITY lat);
+    /** Enumerated values for attribute "Laterality"
+     */
+    enum LATERALITY
+    {
+        /// Undefined (e.g.\ value not set)
+        LATERALITY_UNDEFINED,
+        /// Invalid Laterality, e.g. when invalid value is read from file
+        LATERALITY_INVALID,
+        /// Right body part
+        LATERALITY_R,
+        /// Left body part
+        LATERALITY_L,
+        /// Unpaired body part
+        LATERALITY_UNPAIRED,
+        /// Both, left and right
+        LATERALITY_BOTH
+    };
+
+    /** Constructor, creates empty Frame Anatomy Functional Group
+     */
+    FGFrameAnatomy();
+
+    /** Virtual destructor, frees memory
+     */
+    virtual ~FGFrameAnatomy();
+
+    /** Returns a deep copy of this object
+     *  @return Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Returns shared type of this group (can be shared or per-frame)
+     *  @return Always returns DcmFGTypes::EFGS_BOTH;
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clear all data
+     */
+    virtual void clearData();
+
+    /** Check whether data in functional group is valid
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read functional group from given item
+     *  @param  item The item to read from, must contain Frame Anatomy Sequence
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Write functional group to given item
+     *  @param  item The item to write Frame Anatomy Sequence to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    // --- get() functionality ---
+
+    /** Get Laterality
+     *  @param  value Reference to variable in which the value should be stored
+     *  @return EC_Normal if successful, an error code otherwise (i.e. if
+     *          value is LATERALITY_INVALID).
+     */
+    virtual OFCondition getLaterality(LATERALITY& value);
+
+    /** Get anatomy information
+     *  @return Reference to anatomic information
+     */
+    virtual GeneralAnatomyMacro& getAnatomy();
+
+    // --- set() functionality ---
+
+    /** Set Laterality
+     *  @param  value Value to be set
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setLaterality(const LATERALITY& value);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    static LATERALITY str2Laterality(const OFString& lat);
+
+    static OFString laterality2Str(const LATERALITY lat);
+
+    static OFBool isLateralityValid(const LATERALITY lat);
 
 private:
+    /* Content of Frame Anatomy Macro */
 
-  /* Content of Frame Anatomy Macro */
-
-  /// Frame Laterality (DS, VM 1, Required type 1)
-  LATERALITY m_FrameLaterality;
+    /// Frame Laterality (DS, VM 1, Required type 1)
+    LATERALITY m_FrameLaterality;
 
-  /// General Anatomy Mandatory Macro
-  GeneralAnatomyMacro m_Anatomy;
+    /// General Anatomy Mandatory Macro
+    GeneralAnatomyMacro m_Anatomy;
 };
 
 #endif // FGFRAMEANATOMY_H
index 81cb6605f4333b112e439566c55d33f1f23f79e3..32e837968933205282635b796c7bda1da275db98 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -23,6 +23,7 @@
 #define FGFRAMEVOILUT_H
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcitem.h"
 #include "dcmtk/dcmfg/fgbase.h"
 
 class DCMTK_DCMFG_EXPORT FGFrameVOILUT : public FGBase
 {
 public:
-
-  /** Constructor creating empty functional group
-   */
-  FGFrameVOILUT();
-
-  /** Virtual destructor
-   */
-  virtual ~FGFrameVOILUT();
-
-  /** Returns a deep copy of this object
-   *  @return  Deep copy of this object
-   */
-  virtual FGBase *clone() const;
-
-  /** Get shared type of this kind functional group (can be both, per-frame or
-   *  shared)
-   *  @return Always returns DcmFGTypes::EFGS_BOTH
-   */
-  virtual DcmFGTypes::E_FGSharedType getSharedType() const {return DcmFGTypes::EFGS_BOTH;}
-
-  /** Clear old values
-   */
-  virtual void clearData();
-
-  /** Check whether functional group contains valid data
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  virtual OFCondition check() const;
-
-  /** Read Frame VOI LUT Sequence from given item
-   *  @param  item The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& item);
-
-  /** Write Frame VOI LUT Sequence to given item
-   *  @param  item The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
-
-  // --- get() functionality ---
-
-   /** Get Window Center
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1)
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getWindowCenter(Float64& value,
-                                      const unsigned long pos = 0);
-
-   /** Get Window Width
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1)
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getWindowWidth(Float64& value,
-                                     const unsigned long pos = 0);
-
-   /** Get Window Center and Window Width Explanation
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1)
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getWindowCenterAndWindowWidthExplanation(OFString& value,
-                                                               const unsigned long pos = 0);
-
-   /** Get tripe of information: Window Center, Window With, Window Center and
-    *  Window Width Explanation
-    *  @param  windowCenter Reference to variable in which Window Center should
-    *          be stored
-    *  @param  windowWidth Reference to variable in which Window Width should
-    *          be stored
-    *  @param  explanation Reference to variable in which Window Center and
-    *          Window Width Explanation should be stored
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getCenterWidthExplanation(Float64& windowCenter,
-                                                Float64& windowWidth,
-                                                OFString& explanation);
-
-   /** Get VOI LUT Function
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1)
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getVOILUTFunction(OFString& value,
-                                        const unsigned long pos = 0);
-
-
-  // --- set() functionality ---
-
-  /** Set Window Center
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setWindowCenter(const OFString& value,
-                                      const OFBool checkValue = OFTrue);
-
-  /** Set Window Width
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setWindowWidth(const OFString& value,
-                                     const OFBool checkValue = OFTrue);
-
-  /** Set Window Center and Window Width Explanation
-   *  @param  windowCenter Value for Window Center
-   *  @param  windowWidth Value for Window Width
-   *  @param  explanation Value for Window Center and Window Width Explanation
-   *          should be stored
-   *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1-n)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setCenterWidthExplanation(const Float64& windowCenter,
-                                                const Float64& windowWidth,
-                                                const OFString& explanation = "",
-                                                const OFBool checkValue = OFTrue);
-
-  /** Set VOI LUT Function
-   *  @param  value Value for VOI LUT Function
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setVOILUTFunction(const OFString& value,
-                                        const OFBool checkValue = OFTrue);
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGUnknown) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the this object, or all compared components match
-   *          but this component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in this object, or all compared components match
-   *          but this component is longer.
-   */
-  virtual int compare(const FGBase& rhs) const;
+    /// Defined Term "BRAIN" for tag Window Center & Width Explanation (0028,1055) for CT objects
+    static const OFString DT_CT_WindowCenterWidthExplanation_Brain;
+    /// Defined Term "SOFT_TISSUE" for tag Window Center & Width Explanation (0028,1055) for CT objects
+    static const OFString DT_CT_WindowCenterWidthExplanation_SoftTissue;
+    /// Defined Term "LUNG" for tag Window Center & Width Explanation (0028,1055) for CT objects
+    static const OFString DT_CT_WindowCenterWidthExplanation_Lung;
+    /// Defined Term "BONE" for tag Window Center & Width Explanation (0028,1055) for CT objects
+    static const OFString DT_CT_WindowCenterWidthExplanation_Bone;
+
+    /** Constructor creating empty functional group
+     */
+    FGFrameVOILUT();
+
+    /** Virtual destructor
+     */
+    virtual ~FGFrameVOILUT();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Get shared type of this kind functional group (can be both, per-frame or
+     *  shared)
+     *  @return Always returns DcmFGTypes::EFGS_BOTH
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clear old values
+     */
+    virtual void clearData();
+
+    /** Check whether functional group contains valid data
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read Frame VOI LUT Sequence from given item
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Write Frame VOI LUT Sequence to given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    // --- get() functionality ---
+
+    /** Get Window Center
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getWindowCenter(Float64& value, const unsigned long pos = 0);
+
+    /** Get Window Width
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getWindowWidth(Float64& value, const unsigned long pos = 0);
+
+    /** Get Window Center and Window Width Explanation
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getWindowCenterAndWindowWidthExplanation(OFString& value, const unsigned long pos = 0);
+
+    /** Get tripe of information: Window Center, Window With, Window Center and
+     *  Window Width Explanation
+     *  @param  windowCenter Reference to variable in which Window Center should
+     *          be stored
+     *  @param  windowWidth Reference to variable in which Window Width should
+     *          be stored
+     *  @param  explanation Reference to variable in which Window Center and
+     *          Window Width Explanation should be stored
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getCenterWidthExplanation(Float64& windowCenter, Float64& windowWidth, OFString& explanation);
+
+    /** Get VOI LUT Function
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getVOILUTFunction(OFString& value, const unsigned long pos = 0);
+
+    // --- set() functionality ---
+
+    /** Set Window Center
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setWindowCenter(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Window Width
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setWindowWidth(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Window Center and Window Width Explanation
+     *  @param  windowCenter Value for Window Center
+     *  @param  windowWidth Value for Window Width
+     *  @param  explanation Value for Window Center and Window Width Explanation
+     *          should be stored
+     *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1-n)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setCenterWidthExplanation(const Float64& windowCenter,
+                                                  const Float64& windowWidth,
+                                                  const OFString& explanation = "",
+                                                  const OFBool checkValue     = OFTrue);
+
+    /** Set VOI LUT Function
+     *  @param  value Value for VOI LUT Function
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setVOILUTFunction(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
 
 private:
+    /* Content of Frame VOI LUT Macro */
 
-  /* Content of Frame VOI LUT Macro */
-
-  /// Window Center (DS, VM 1-n, Required type 1)
-  DcmDecimalString m_WindowCenter;
+    /// Window Center (DS, VM 1-n, Required type 1)
+    DcmDecimalString m_WindowCenter;
 
-  /// Window Width (DS, VM 1-n, Required type 1)
-  DcmDecimalString m_WindowWidth;
+    /// Window Width (DS, VM 1-n, Required type 1)
+    DcmDecimalString m_WindowWidth;
 
-  /// Window Center & Window Width Explanation (LO, VM 1-n, Required type 3)
-  DcmLongString m_WindowCenterWindowWidthExplanation;
+    /// Window Center & Window Width Explanation (LO, VM 1-n, Required type 3)
+    DcmLongString m_WindowCenterWindowWidthExplanation;
 
-  /// VOI LUT Function (CS, VM 1, Requirement Type 3)
-  DcmCodeString m_VOILUTFunction;
+    /// VOI LUT Function (CS, VM 1, Requirement Type 3)
+    DcmCodeString m_VOILUTFunction;
 };
 
 #endif // FGFRAMEVOILUT_H
index 1ba990f4d1b25b8c7dbc0725f41e467a406b204e..1cb94bf73ef7d5a31260db6ae5aaf20b80e4928d 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -23,6 +23,7 @@
 #define FGIMAGEDATATYPE_H
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcitem.h"
 #include "dcmtk/dcmfg/fgbase.h"
 
 class DCMTK_DCMFG_EXPORT FGImageDataType : public FGBase
 {
 public:
-
-  /** Constructor, creates empty Image Data Type functional group
-   */
-  FGImageDataType();
-
-  /** Destructor, frees memory
-   */
-  virtual ~FGImageDataType();
-
-  /** Returns a deep copy of this object
-   *  @return  Deep copy of this object
-   */
-  virtual FGBase *clone() const;
-
-  /** Get potential shared type of this group, always returns
-   *  DcmFGTypes::EFGS_BOTH
-   *  @return Always returns DcmFGTypes::EFGS_BOTH
-   */
-  virtual DcmFGTypes::E_FGSharedType getSharedType() const {return DcmFGTypes::EFGS_BOTH;}
-
-  /** Clear data
-   */
-  virtual void clearData();
-
-  /** Check whether current data of this functional group is valid
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  virtual OFCondition check() const;
-
-  /** Read Image Data Type Sequence (this functional group) from given item
-   * @param  item Item to read from
-   * @return EC_Normal if reading works, error otherwise
-   */
-  virtual OFCondition read(DcmItem &item);
-
-  /** Write Image Data Type Sequence (this functional group) to given item
-   * @param  item Item to write to
-   * @return EC_Normal if writing works, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
-
-  // --- get() functionality ---
-
-  /** Get Data Type
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getDataType(OFString& value,
-                                  const signed long pos = 0);
-
-  /** Get Aliased Data Type
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getAliasedDataType(OFString& value,
-                                         const signed long pos = 0);
-
-  /** Get Zero Velocity Pixel Value
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getZeroVelocityPixelValue(Sint32& value,
-                                                const signed long pos = 0);
-
-  // --- set() functionality ---
-
-  /** Set Data Type
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setDataType(const OFString& value,
-                                  const OFBool checkValue = OFTrue);
-
-  /** Set Aliased Data Type
-   *  @param  value Permitted values: "YES" or "NO".
-   *  @param  checkValue If enabled, the value is checked for conformance
-   *  @return EC_Normal if value was set, error code otherwise
-   */
-  virtual OFCondition setAliasedDataType(const OFString& value,
-                                         const OFBool checkValue = OFTrue);
-
-  /** Set Zero Velocity Pixel Value. Only use if Zero Velocity Pixel Value is of
-   *  VR US, i.e.\ Pixel Representation = 0
-   *  @param  value Value to be set
-
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setZeroVelocityPixelValueUS(const Uint16 value);
-
-  /** Set Zero Velocity Pixel Value. Only use if Zero Velocity Pixel Value is of
-   *  VR SS, i.e.\ Pixel Representation = 1
-   *  @param  value Value to be set
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setZeroVelocityPixelValueSS(const Sint16 value);
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGUnknown) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the this object, or all compared components match
-   *          but this component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in this object, or all compared components match
-   *          but this component is longer.
-   */
-  virtual int compare(const FGBase& rhs) const;
+    /** Constructor, creates empty Image Data Type functional group
+     */
+    FGImageDataType();
+
+    /** Destructor, frees memory
+     */
+    virtual ~FGImageDataType();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Get potential shared type of this group, always returns
+     *  DcmFGTypes::EFGS_BOTH
+     *  @return Always returns DcmFGTypes::EFGS_BOTH
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clear data
+     */
+    virtual void clearData();
+
+    /** Check whether current data of this functional group is valid
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read Image Data Type Sequence (this functional group) from given item
+     * @param  item Item to read from
+     * @return EC_Normal if reading works, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Write Image Data Type Sequence (this functional group) to given item
+     * @param  item Item to write to
+     * @return EC_Normal if writing works, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    // --- get() functionality ---
+
+    /** Get Data Type
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getDataType(OFString& value, const signed long pos = 0);
+
+    /** Get Aliased Data Type
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getAliasedDataType(OFString& value, const signed long pos = 0);
+
+    /** Get Zero Velocity Pixel Value
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getZeroVelocityPixelValue(Sint32& value, const unsigned long pos = 0);
+
+    // --- set() functionality ---
+
+    /** Set Data Type
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setDataType(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Aliased Data Type
+     *  @param  value Permitted values: "YES" or "NO".
+     *  @param  checkValue If enabled, the value is checked for conformance
+     *  @return EC_Normal if value was set, error code otherwise
+     */
+    virtual OFCondition setAliasedDataType(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Zero Velocity Pixel Value. Only use if Zero Velocity Pixel Value is of
+     *  VR US, i.e.\ Pixel Representation = 0
+     *  @param  value Value to be set
+
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setZeroVelocityPixelValueUS(const Uint16 value);
+
+    /** Set Zero Velocity Pixel Value. Only use if Zero Velocity Pixel Value is of
+     *  VR SS, i.e.\ Pixel Representation = 1
+     *  @param  value Value to be set
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setZeroVelocityPixelValueSS(const Sint16 value);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
 
 private:
+    /* Content of Image Data Type Macro */
 
-  /* Content of Image Data Type Macro */
-
-  /// Data Type (CS, VM 1, Required type 1)
-  DcmCodeString m_DataType;
-
-  /// Aliased Data Type (CS, VM 1, Required Type 1)
-  DcmCodeString m_AliasedDataType;
+    /// Data Type (CS, VM 1, Required type 1)
+    DcmCodeString m_DataType;
 
-  /// Zero Velocity Pixel Value (US or SS, VM , Required Type 1C)
-  DcmUnsignedShort m_ZeroVelocityPixelValueUS;
+    /// Aliased Data Type (CS, VM 1, Required Type 1)
+    DcmCodeString m_AliasedDataType;
 
-  /// Zero Velocity Pixel Value (US or SS, VM , Required Type 1C)
-  DcmSignedShort m_ZeroVelocityPixelValueSS;
+    /// Zero Velocity Pixel Value (US or SS, VM , Required Type 1C)
+    DcmUnsignedShort m_ZeroVelocityPixelValueUS;
 
+    /// Zero Velocity Pixel Value (US or SS, VM , Required Type 1C)
+    DcmSignedShort m_ZeroVelocityPixelValueSS;
 };
 
 #endif // FGIMAGEDATATYPE_H
index bd9c6cc5b43027277c9b4607edbc51f17daf193c..8570efea77f4a19e495322d3b2f310130d803f03 100644 (file)
 #define FGINTERFACE_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofvector.h"
-#include "dcmtk/ofstd/ofmap.h"
-#include "dcmtk/dcmdata/dcsequen.h"
+
 #include "dcmtk/dcmdata/dcdatset.h"
+#include "dcmtk/dcmdata/dcsequen.h"
 #include "dcmtk/dcmdata/dctk.h"
-#include "dcmtk/dcmiod/iodrules.h"
-#include "dcmtk/dcmfg/fgtypes.h"
-#include "dcmtk/dcmfg/fgdefine.h"
 #include "dcmtk/dcmfg/fg.h"
+#include "dcmtk/dcmfg/fgdefine.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/dcmiod/iodrules.h"
+#include "dcmtk/ofstd/ofmap.h"
+#include "dcmtk/ofstd/ofvector.h"
 
 // Forward declaration
 class IODMultiframeDimensionModule;
@@ -44,274 +45,261 @@ class DCMTK_DCMFG_EXPORT FGInterface
 {
 
 public:
-
-  /// Type representing per-frame functional groups, i.e.\ a number of
-  /// functional groups assigned to each frame
-  typedef OFMap<Uint32, FunctionalGroups*> PerFrameGroups;
-
-  /// Iterator type for iterating over functional groups
-  typedef FunctionalGroups::iterator iterator;
-
-  /// Const iterator type for iterating over functional groups
-  typedef FunctionalGroups::const_iterator const_iterator;
-
-  /** Constructor, constructs empty sets of per-frame and shared
-   *  functional groups
-   */
-  FGInterface();
-
-  /** Virtual destructor, frees memory
-   */
-  virtual ~FGInterface();
-
-  /** Delete all functional groups (shared and per-frame)
-   */
-  virtual void clear();
-
-  /** Checks the functional groups for consistency. The following checks are
-   *  performed:
-   *    -# Check that every frame has a FrameContent functional group.
-   *    -# Check that any per-frame group is not shared at the same time.
-   *    -# Check for each per-frame group, that it is allowed to be per-frame.
-   *    -# Check for each shared group, that it is allowed to be shared.
-   *  @return OFTrue, if check consistency is ok, error otherwise
-   */
-  virtual OFBool check();
-
-  /** Returns number of frames. Computed by number of per-frame
-   *  functional group items (i.e.\ the Number of Frames attribute
-   *  is not taken into account).
-   *  @return Number of frames
-   */
-  virtual size_t getNumberOfFrames();
-
-  /** Read enhanced multi-frame information from DICOM item, usually
-   *  DcmDataset, i.e.\ must contain Shared and Per-frame Functional Group
-   *  Sequences
-   *  @param  dataset The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& dataset);
-
-  /** Write enhanced multi-frame information to DICOM item,
-   *  usually DcmDataset, i.e.\ writes  Shared and Per-frame Functional Group
-   *  Sequences
-   *  @param  dataset The item to write to
-   *  @return EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& dataset);
-
-  /** Get specific functional group for a frame, no matter whether it is stored
-   *  per frame or shared
-   *  @param  frameNo The frame number the functional group should apply to
-   *          (starts with 0)
-   *  @param  fgType The type of functional group to look for
-   *  @return The functional group if found, NULL otherwise
-   */
-  virtual FGBase* get(const Uint32 frameNo,
-                      const DcmFGTypes::E_FGType fgType);
-
-  // TODO Add get(..) version that takes the sequence tag (e.g.\ for unknown
-  // functional groups
-
-  /** Get specific functional group for a frame, no matter whether it is stored
-   *  per frame or shared.
-   *  @param  frameNo The frame number of group of interest (starts from 0)
-   *  @param  fgType The type of functional group to look for
-   *  @param  isPerFrame If OFTrue, the group found was found as per-frame,
-   *          otherwise it is a shared functional group
-   *  @return The functional group if found, error otherwise
-   */
-  virtual FGBase* get(const Uint32 frameNo,
-                      const DcmFGTypes::E_FGType fgType,
-                      OFBool& isPerFrame);
-
-  /** Return all per-frame functional groups, e.g.\ to iterate over them
-   *  @param  frameNo The frame number of the groups of interest (starts from 0)
-   *  @return The per-frame functional groups for the given frame
-   */
-  const FunctionalGroups* getPerFrame(const Uint32 frameNo) const;
-
-  /** Return all shared functional groups, e.g.\ to iterate over them
-   *  @return The shared functional groups
-   */
-  const FunctionalGroups* getShared() const;
-
-  /** Add functional group that should be shared for all frames. This will
-   *  delete all per-frame groups of the same type if existing.
-   *  @param  group   The group to be added. The group is copied.
-   *  @return EC_Normal, if adding was successful, error otherwise
-   */
-  virtual OFCondition addShared(const FGBase& group);
-
-  /** Add functional group for given frame. If there is already a shared
-   *  functional group with identical values, the call returns without
-   *  errors, too. If there is a shared group that differs, the shared group
-   *  is converted to be "per-frame" for all frames and then the given group
-   *  is inserted for the frame specified by the user.
-   *  If a per-frame functional group of the same type already exists it is
-   *  overwritten.
-   *  @param  frameNo The frame number this group should be added for (starts
-   *          from 0)
-   *  @param  group The group to be added. The group is copied when adding,
-   *          so the ownership stays with the caller, no matter what the
-   *          method returns.
-   *  @return EC_Normal, if adding was successful, error otherwise
-   */
-  virtual OFCondition addPerFrame(const Uint32 frameNo,
-                                  const FGBase& group);
-
-  /** Deletes a shared functional group of the given type
-   *  @param fgType The type of functional group to delete
-   *  @return OFTrue if group existed and could be deleted, OFFalse (group did
-   *          not exist) otherwise
-   */
-  virtual OFBool deleteShared(const DcmFGTypes::E_FGType fgType);
-
-  /** Deletes per-frame functional group of the given type for a specific frame
-   *  @param frameNo The frame number for the functional group of interest.
-   *         First frame is frame 0.
-   *  @param fgType The type of functional group to delete
-   *  @return OFTrue if group existed and could be deleted, OFFalse (group did
-   *          not exist) otherwise
-   */
-  virtual OFBool deletePerFrame(const Uint32 frameNo,
-                                const DcmFGTypes::E_FGType fgType);
-
-  /** Deletes per-frame functional group for all frames
-   *  @param  fgType The type of functional group to delete
-   *  @return Number of per-frame groups deleted (usually equal to number of
-   *          frames)
-   */
-  size_t deletePerFrame(const DcmFGTypes::E_FGType fgType);
-
-  /** Deletes all functional groups for a specific frame
-   *  @param frameNo The frame number whose functional groups should be deleted.
-   *         First frame is frame 0.
-   *  @return Number of per-frame groups deleted for this frame
-   */
-  size_t deleteFrame(const Uint32 frameNo);
-
-  /** If enabled, functional group structure is checked before actual writing
-   *  is performed in the write() method. Checking might be time consuming
-   *  on functional groups with many frames, though disabling might result in
-   *  invalid functional group structures. Disabling should only be done if the
-   *  user knows that the functional groups are valid, wants to to adapt the
-   *  functional groups manually after calling write() or knows what he's doing
-   *  otherwise.<br>
-   *  Per default, checking is enabled.
-   *  @param  doCheck If OFTrue, checking will be performed. If OFFalse,
-   *          no checks are performed.
-   */
-  virtual void setCheckOnWrite(const OFBool doCheck);
-
-  /** Returns whether functional group structure is checked before actual
-   *  writing is performed in the write() method.
-   *  @return OFTrue if checking is performed, OFFalse otherwise
-   */
-  virtual OFBool getCheckOnWrite();
+    /// Type representing per-frame functional groups, i.e.\ a number of
+    /// functional groups assigned to each frame
+    typedef OFMap<Uint32, FunctionalGroups*> PerFrameGroups;
+
+    /// Iterator type for iterating over functional groups
+    typedef FunctionalGroups::iterator iterator;
+
+    /// Const iterator type for iterating over functional groups
+    typedef FunctionalGroups::const_iterator const_iterator;
+
+    /** Constructor, constructs empty sets of per-frame and shared
+     *  functional groups
+     */
+    FGInterface();
+
+    /** Virtual destructor, frees memory
+     */
+    virtual ~FGInterface();
+
+    /** Delete all functional groups (shared and per-frame)
+     */
+    virtual void clear();
+
+    /** Checks the functional groups for consistency. The following checks are
+     *  performed:
+     *    -# Check that every frame has a FrameContent functional group.
+     *    -# Check that any per-frame group is not shared at the same time.
+     *    -# Check for each per-frame group, that it is allowed to be per-frame.
+     *    -# Check for each shared group, that it is allowed to be shared.
+     *  @return OFTrue, if check consistency is ok, error otherwise
+     */
+    virtual OFBool check();
+
+    /** Returns number of frames. Computed by number of per-frame
+     *  functional group items (i.e.\ the Number of Frames attribute
+     *  is not taken into account).
+     *  @return Number of frames
+     */
+    virtual size_t getNumberOfFrames();
+
+    /** Read enhanced multi-frame information from DICOM item, usually
+     *  DcmDataset, i.e.\ must contain Shared and Per-frame Functional Group
+     *  Sequences
+     *  @param  dataset The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& dataset);
+
+    /** Write enhanced multi-frame information to DICOM item,
+     *  usually DcmDataset, i.e.\ writes  Shared and Per-frame Functional Group
+     *  Sequences
+     *  @param  dataset The item to write to
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& dataset);
+
+    /** Get specific functional group for a frame, no matter whether it is stored
+     *  per frame or shared
+     *  @param  frameNo The frame number the functional group should apply to
+     *          (starts with 0)
+     *  @param  fgType The type of functional group to look for
+     *  @return The functional group if found, NULL otherwise
+     */
+    virtual FGBase* get(const Uint32 frameNo, const DcmFGTypes::E_FGType fgType);
+
+    // TODO Add get(..) version that takes the sequence tag (e.g.\ for unknown
+    // functional groups
+
+    /** Get specific functional group for a frame, no matter whether it is stored
+     *  per frame or shared.
+     *  @param  frameNo The frame number of group of interest (starts from 0)
+     *  @param  fgType The type of functional group to look for
+     *  @param  isPerFrame If OFTrue, the group found was found as per-frame,
+     *          otherwise it is a shared functional group
+     *  @return The functional group if found, error otherwise
+     */
+    virtual FGBase* get(const Uint32 frameNo, const DcmFGTypes::E_FGType fgType, OFBool& isPerFrame);
+
+    /** Return all per-frame functional groups, e.g.\ to iterate over them
+     *  @param  frameNo The frame number of the groups of interest (starts from 0)
+     *  @return The per-frame functional groups for the given frame
+     */
+    const FunctionalGroups* getPerFrame(const Uint32 frameNo) const;
+
+    /** Return all shared functional groups, e.g.\ to iterate over them
+     *  @return The shared functional groups
+     */
+    const FunctionalGroups* getShared() const;
+
+    /** Add functional group that should be shared for all frames. This will
+     *  delete all per-frame groups of the same type if existing.
+     *  @param  group   The group to be added. The group is copied.
+     *  @return EC_Normal, if adding was successful, error otherwise
+     */
+    virtual OFCondition addShared(const FGBase& group);
+
+    /** Add functional group for given frame. If there is already a shared
+     *  functional group with identical values, the call returns without
+     *  errors, too. If there is a shared group that differs, the shared group
+     *  is converted to be "per-frame" for all frames and then the given group
+     *  is inserted for the frame specified by the user.
+     *  If a per-frame functional group of the same type already exists it is
+     *  overwritten.
+     *  @param  frameNo The frame number this group should be added for (starts
+     *          from 0)
+     *  @param  group The group to be added. The group is copied when adding,
+     *          so the ownership stays with the caller, no matter what the
+     *          method returns.
+     *  @return EC_Normal, if adding was successful, error otherwise
+     */
+    virtual OFCondition addPerFrame(const Uint32 frameNo, const FGBase& group);
+
+    /** Deletes a shared functional group of the given type
+     *  @param fgType The type of functional group to delete
+     *  @return OFTrue if group existed and could be deleted, OFFalse (group did
+     *          not exist) otherwise
+     */
+    virtual OFBool deleteShared(const DcmFGTypes::E_FGType fgType);
+
+    /** Deletes per-frame functional group of the given type for a specific frame
+     *  @param frameNo The frame number for the functional group of interest.
+     *         First frame is frame 0.
+     *  @param fgType The type of functional group to delete
+     *  @return OFTrue if group existed and could be deleted, OFFalse (group did
+     *          not exist) otherwise
+     */
+    virtual OFBool deletePerFrame(const Uint32 frameNo, const DcmFGTypes::E_FGType fgType);
+
+    /** Deletes per-frame functional group for all frames
+     *  @param  fgType The type of functional group to delete
+     *  @return Number of per-frame groups deleted (usually equal to number of
+     *          frames)
+     */
+    size_t deletePerFrame(const DcmFGTypes::E_FGType fgType);
+
+    /** Deletes all functional groups for a specific frame
+     *  @param frameNo The frame number whose functional groups should be deleted.
+     *         First frame is frame 0.
+     *  @return Number of per-frame groups deleted for this frame
+     */
+    size_t deleteFrame(const Uint32 frameNo);
+
+    /** If enabled, functional group structure is checked before actual writing
+     *  is performed in the write() method. Checking might be time consuming
+     *  on functional groups with many frames, though disabling might result in
+     *  invalid functional group structures. Disabling should only be done if the
+     *  user knows that the functional groups are valid, wants to to adapt the
+     *  functional groups manually after calling write() or knows what he's doing
+     *  otherwise.<br>
+     *  Per default, checking is enabled.
+     *  @param  doCheck If OFTrue, checking will be performed. If OFFalse,
+     *          no checks are performed.
+     */
+    virtual void setCheckOnWrite(const OFBool doCheck);
+
+    /** Returns whether functional group structure is checked before actual
+     *  writing is performed in the write() method.
+     *  @return OFTrue if checking is performed, OFFalse otherwise
+     */
+    virtual OFBool getCheckOnWrite();
 
 protected:
-
-  /** Get shared functional group based on its type
-   *  @param  fgType The type of functional group
-   *  @return The functional group or NULL if not existent
-   */
-  virtual FGBase* getShared(const DcmFGTypes::E_FGType fgType);
-
-  /** Insert shared functional group
-   *  @param  group The functional group to be inserted
-   *  @param  replaceExisting If OFTrue, an existing shared functional group
-   *          will be deleted, otherwise the old group is not overwritten
-   *  @return EC_Normal if insertion worked, FG_EC_DoubledFG if group exists and
-   *          is not overwritten, other error code for other cases
-   */
-  virtual OFCondition insertShared(FGBase* group,
-                                   const OFBool replaceExisting = OFTrue);
-
-  /** Get per-frame functional group
-   *  @param  frameNo  The frame number of the group
-   *  @param  fgType The type of the group
-   *  @return The functional group or NULL if not existent
-   */
-  virtual FGBase* getPerFrame(const Uint32 frameNo,
-                              const DcmFGTypes::E_FGType fgType);
-
-  /** Insert per-frame functional group
-   *  @param  frameNo The frame number the group should be added for
-   *  @param  group The functional group to be inserted
-   *  @param  replaceExisting If OFTrue, an existing per-frame functional group
-   *          will be deleted, otherwise the old group is not overwritten
-   *  @return EC_Normal if insertion worked, FG_EC_DoubledFG if group exists and
-   *          is not overwritten, other error code for other cases
-   */
-  virtual OFCondition insertPerFrame(const Uint32 frameNo,
-                                     FGBase* group,
-                                     const OFBool replaceExisting = OFTrue);
-
-  /** Get existing per-frame group or create it for the given frame. Note that
-   *  the per-frame groups do not have to be created "in order", i.e.\ one could
-   *  add groups in order 3,5,1 ,... .
-   *  @param  frameNo The frame number to get/create per-frame groups for
-   *  @return The functional groups if found/created, NULL in case of error
-   */
-  virtual FunctionalGroups* getOrCreatePerFrameGroups(const Uint32 frameNo);
-
-  /** Read Shared Functional Group Sequence from given item
-   *  @param  dataset The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition readSharedFG(DcmItem& dataset);
-
-  /** Read Per-Frame Functional Group Sequence from given item
-   *  @param  dataset The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition readPerFrameFG(DcmItem& dataset);
-
-  /** Read single functional group into the item provided
-   *  @param  fgItem The item to read from
-   *  @param  groups The resulting group after reading
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition readSingleFG(DcmItem& fgItem,
-                                   FunctionalGroups& groups);
-
-  /** Write Shared Functional Group Sequence to given item
-   *  @param  dataset The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition writeSharedFG(DcmItem& dataset);
-
-  /** Write Per-Frame Functional Group Sequence to given item
-   *  @param  dataset The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition writePerFrameFG(DcmItem& dataset);
-
-  /** Convert a shared functional group to a per-frame one by copying the
-   *  shared one into a per-frame one for each frame and deleting the shared one
-   *  aftewrards.
-   *  @param  fgType The type of functional group to convert
-   *  @return EC_Normal if conversion worked out, FG_EC_NoSuchGroup if such a
-   *          group does not exist and other error otherwise. In the last case
-   *          the functional groups may be left in invalid state, but that
-   *          should only happen for fatal errors like exhausted memory.
-   */
-  virtual OFCondition convertSharedToPerFrame(const DcmFGTypes::E_FGType fgType);
+    /** Get shared functional group based on its type
+     *  @param  fgType The type of functional group
+     *  @return The functional group or NULL if not existent
+     */
+    virtual FGBase* getShared(const DcmFGTypes::E_FGType fgType);
+
+    /** Insert shared functional group
+     *  @param  group The functional group to be inserted
+     *  @param  replaceExisting If OFTrue, an existing shared functional group
+     *          will be deleted, otherwise the old group is not overwritten
+     *  @return EC_Normal if insertion worked, FG_EC_DoubledFG if group exists and
+     *          is not overwritten, other error code for other cases
+     */
+    virtual OFCondition insertShared(FGBase* group, const OFBool replaceExisting = OFTrue);
+
+    /** Get per-frame functional group
+     *  @param  frameNo  The frame number of the group
+     *  @param  fgType The type of the group
+     *  @return The functional group or NULL if not existent
+     */
+    virtual FGBase* getPerFrame(const Uint32 frameNo, const DcmFGTypes::E_FGType fgType);
+
+    /** Insert per-frame functional group
+     *  @param  frameNo The frame number the group should be added for
+     *  @param  group The functional group to be inserted
+     *  @param  replaceExisting If OFTrue, an existing per-frame functional group
+     *          will be deleted, otherwise the old group is not overwritten
+     *  @return EC_Normal if insertion worked, FG_EC_DoubledFG if group exists and
+     *          is not overwritten, other error code for other cases
+     */
+    virtual OFCondition insertPerFrame(const Uint32 frameNo, FGBase* group, const OFBool replaceExisting = OFTrue);
+
+    /** Get existing per-frame group or create it for the given frame. Note that
+     *  the per-frame groups do not have to be created "in order", i.e.\ one could
+     *  add groups in order 3,5,1 ,... .
+     *  @param  frameNo The frame number to get/create per-frame groups for
+     *  @return The functional groups if found/created, NULL in case of error
+     */
+    virtual FunctionalGroups* getOrCreatePerFrameGroups(const Uint32 frameNo);
+
+    /** Read Shared Functional Group Sequence from given item
+     *  @param  dataset The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition readSharedFG(DcmItem& dataset);
+
+    /** Read Per-Frame Functional Group Sequence from given item
+     *  @param  dataset The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition readPerFrameFG(DcmItem& dataset);
+
+    /** Read single functional group into the item provided
+     *  @param  fgItem The item to read from
+     *  @param  groups The resulting group after reading
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition readSingleFG(DcmItem& fgItem, FunctionalGroups& groups);
+
+    /** Write Shared Functional Group Sequence to given item
+     *  @param  dataset The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition writeSharedFG(DcmItem& dataset);
+
+    /** Write Per-Frame Functional Group Sequence to given item
+     *  @param  dataset The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition writePerFrameFG(DcmItem& dataset);
+
+    /** Convert a shared functional group to a per-frame one by copying the
+     *  shared one into a per-frame one for each frame and deleting the shared one
+     *  aftewrards.
+     *  @param  fgType The type of functional group to convert
+     *  @return EC_Normal if conversion worked out, FG_EC_NoSuchGroup if such a
+     *          group does not exist and other error otherwise. In the last case
+     *          the functional groups may be left in invalid state, but that
+     *          should only happen for fatal errors like exhausted memory.
+     */
+    virtual OFCondition convertSharedToPerFrame(const DcmFGTypes::E_FGType fgType);
 
 private:
+    /// Shared functional groups
+    FunctionalGroups m_shared;
 
-  /// Shared functional groups
-  FunctionalGroups m_shared;
-
-  /// Link from frame number (map key) to the list of functional groups (value)
-  /// relevant for the frame
-  PerFrameGroups m_perFrame;
+    /// Link from frame number (map key) to the list of functional groups (value)
+    /// relevant for the frame
+    PerFrameGroups m_perFrame;
 
-  /// If enabled, functional group structure is checked on write(). Otherwise,
-  /// checks are skipped.
-  OFBool m_checkOnWrite;
+    /// If enabled, functional group structure is checked on write(). Otherwise,
+    /// checks are skipped.
+    OFBool m_checkOnWrite;
 };
 
 #endif // MODMULTIFRAMEFGH_H
diff --git a/dcmfg/include/dcmtk/dcmfg/fgirradiationeventid.h b/dcmfg/include/dcmtk/dcmfg/fgirradiationeventid.h
new file mode 100644 (file)
index 0000000..5c1a820
--- /dev/null
@@ -0,0 +1,131 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the Irradiation Event Identification Functional Group
+ *
+ */
+
+#ifndef FGIRRADIATIONEVENTID_H
+#define FGIRRADIATIONEVENTID_H
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dctk.h"
+#include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/ofstd/ofstring.h"
+#include "dcmtk/ofstd/ofvector.h"
+
+/** Class representing the "Irradiation Event Identification" Functional Group Macro.
+ */
+class DCMTK_DCMFG_EXPORT FGIrradiationEventIdentification : public FGBase
+{
+public:
+    /** Constructor, creates empty functional group
+     */
+    FGIrradiationEventIdentification();
+
+    /** Virtual destructor
+     */
+    virtual ~FGIrradiationEventIdentification();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Returns shared functional group type (always "per-frame")
+     *  @return The functional group type (DcmFGTypes::EFGS_ONLYPERFRAME)
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clear all data
+     */
+    virtual void clearData();
+
+    /** Check whether the current content of this group is consistent and complete
+     *  @return EC_Normal, if no errors are found, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read Frame Content Sequence from given item
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Writes the content of this class into Frame Content Sequence
+     *  (newly cerated) into given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    // --- get() functionality ---
+
+    /** Get Irradiation Event UID
+     *  @param  value Reference to variable that should hold the result
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal, if value could be returned, error otherwise
+     */
+    virtual OFCondition getIrradiationEventUID(OFString& value, const signed long pos = 0);
+
+    // --- set() functionality ---
+
+    /** Set Irradiation Event UID
+     *  @param  value Value that should be set
+     *  @param  checkValue If OFTrue, basic checks are performed whether the value is
+     *          valid for this attribute
+     *  @return EC_Normal, if value was set, error otherwise
+     */
+    virtual OFCondition setIrradiationEventUID(const OFString& value, const OFBool checkValue = OFTrue);
+
+private:
+    /* Content of Irradiation Event Identification FG */
+
+    /// Irradiation Event UID (UI, VM 1, Required type 1)
+    DcmUniqueIdentifier m_IrraditionEventUID;
+};
+
+#endif // FGIRRADIATIONEVENTID_H
index fd463464a32eae795354a4d3f65ab539ca00048d..b059d46605ba8cd97373ad74e8da93700943a74f 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define FGPARAMETRICMAPFRAMETYPE_H
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcitem.h"
-#include "dcmtk/dcmfg/fgbase.h"
 #include "dcmtk/dcmdata/dcvrcs.h"
+#include "dcmtk/dcmfg/fgbase.h"
 
 /** Class representing the Parametric Map Frame Type Functional Group Macro.
  */
 class DCMTK_DCMFG_EXPORT FGParametricMapFrameType : public FGBase
 {
 public:
-  /** Constructor, creates empty Parametric Map Frame Type Functional Group
-   */
-  FGParametricMapFrameType();
-
-  /** Destructor, frees memory
-   */
-  virtual ~FGParametricMapFrameType();
-
-  /** Returns a deep copy of this object
-   *  @return  Deep copy of this object
-   */
-  virtual FGBase *clone() const;
-
-  /** Get shared type of this functional group (can be both, per-frame and
-   *  shared)
-   *  @return Always returns EFGS_BOTH
-   */
-  virtual DcmFGTypes::E_FGSharedType getSharedType() const {return DcmFGTypes::EFGS_BOTH;}
-
-  /** Clears all data
-   */
-  virtual void clearData();
-
-  /** Check whether functional group contains valid data
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  virtual OFCondition check() const;
-
-  /** Read functional group from given item, i.e.\ read Parametric Map Frame Type Sequence
-   *  @param  item The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& item);
-
-  /** Write functional group to given item, i.e.\ write Parametric Map Frame Type Sequence
-   *  @param  item The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
-
-  /** Get FrameType
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getFrameType(OFString &value,
-                                   const signed long pos = 0) const;
-
-  /** Set FrameType
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (4) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setFrameType(const OFString &value,
-                                   const OFBool checkValue = OFTrue);
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGUnknown) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the this object, or all compared components match
-   *          but this component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in this object, or all compared components match
-   *          but this component is longer.
-   */
-  virtual int compare(const FGBase& rhs) const;
+    /** Constructor, creates empty Parametric Map Frame Type Functional Group
+     */
+    FGParametricMapFrameType();
+
+    /** Destructor, frees memory
+     */
+    virtual ~FGParametricMapFrameType();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Get shared type of this functional group (can be both, per-frame and
+     *  shared)
+     *  @return Always returns EFGS_BOTH
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clears all data
+     */
+    virtual void clearData();
+
+    /** Check whether functional group contains valid data
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read functional group from given item, i.e.\ read Parametric Map Frame Type Sequence
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Write functional group to given item, i.e.\ write Parametric Map Frame Type Sequence
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Get FrameType
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getFrameType(OFString& value, const signed long pos = 0) const;
+
+    /** Set FrameType
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (4) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setFrameType(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
 
 private:
+    /* Content of Parametric Map Frame Type Functional Group Macro */
 
-  /* Content of Parametric Map Frame Type Functional Group Macro */
-
-  /// FrameType (CS, VM 4, Required type 1)
-  DcmCodeString m_FrameType;
+    /// FrameType (CS, VM 4, Required type 1)
+    DcmCodeString m_FrameType;
 };
 
 #endif // FGPARAMETRICMAPFRAMETYPE_H
index d98771fa7942303b325f805049ecc3724c717cbc..5cf8e87aa93d59815bcac34ef38953ccc32cf55b 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016-2017, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define FGPIXELTRANSFORM_H
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcitem.h"
-#include "dcmtk/dcmfg/fgbase.h"
 #include "dcmtk/dcmdata/dcvrds.h"
 #include "dcmtk/dcmdata/dcvrlo.h"
+#include "dcmtk/dcmfg/fgbase.h"
 
-
-/** Class representing the Identity Pixel Value Transformation as well as the
- *  Pixel Value Transformation Functional Group Macro.
- *  The former just differs in a way that Rescale Slope, Intercept and Type
- *  have fixed values (1, 0 and "US" respectively).
- *  Rescale Intercept to 0. Right now the
+/** Class representing different flavors of the Pixel Value Transformation FG:
+ *      - Pixel Value Transformation
+ *      - Identity Pixel Value Transformation
+ *      - CT Pixel Value Transformation
+ *  The attributes in each type are always the same.
+ *  Value checking is performed if possible for the selected FG type.
+ *  Otherwise only logging is adapted where applicable.
  */
 class DCMTK_DCMFG_EXPORT FGPixelValueTransformation : public FGBase
 {
 public:
-
-  /** Constructor, creates (Identity) Pixel Value Transformation Functional Group.
-   *  All values (Rescale Slope, Intercept and Type) are initialized as if the
-   *  class is used as the Identity Pixel Value Transformation FG, i.e. Rescale
-   *  Slope is set to 1, Intercept to 0 and Type to "US".
-   */
+    /// Enumerated values for the type of functional group that this
+    /// class should represent.
+    enum E_PixelValueTransformationSubType
+    {
+        /// Value representing the "Pixel Value Transformation Functional Group Macro"
+        E_PixelValTrans_Normal,
+        /// Value representing the "Identity Pixel Value Transformation Functional Group Macro"
+        E_PixelValTrans_Identity,
+        /// Value representing the "CT Pixel Value Transformation Functional Group Macro"
+        E_PixelValTrans_CT
+    };
+
+    /** Constructor, creates (Identity) Pixel Value Transformation Functional Group.
+     *  All values (Rescale Slope, Intercept and Type) are initialized as if the
+     *  class is used as the Identity Pixel Value Transformation FG, i.e. Rescale
+     *  Slope is set to 1, Intercept to 0 and Type to "US".
+     */
     FGPixelValueTransformation();
 
-  /** Destructor, frees memory
-   */
-  virtual ~FGPixelValueTransformation();
-
-  /** Tell this class that it should behave like the Identity Pixel Value
-   *  Transformation Functional Group. This does not make a difference when
-   *  reading data, but when writing, it is assured that Rescale Slope,
-   *  Intercept and Type are forced to be set to 1, 0 and "US" respectively.
-   */
-  virtual void setUseAsIdentityPixelValueTransformation();
-
-  /** Returns a deep copy of this object
-   *  @return  Deep copy of this object
-   */
-  virtual FGBase *clone() const;
-
-  /** Get shared type of this functional group (can be both, per-frame and
-   *  shared)
-   *  @return Always returns EFGS_BOTH
-   */
-  virtual DcmFGTypes::E_FGSharedType getSharedType() const {return DcmFGTypes::EFGS_BOTH;}
-
-  /** Clears all data
-   */
-  virtual void clearData();
-
-  /** Check whether functional group contains valid data
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  virtual OFCondition check() const;
-
-  /** Read functional group from given item, i.e.\ read (Identity) Pixel Value
-   *  Transformation Sequence. Clears existing data before reading.
-   *  @param  item The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& item);
-
-  /** Write functional group to given item, i.e.\ write (Identity) Pixel Value
-   *  Transformation Sequence
-   *  @param  item The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
-
-  /** Get RescaleIntercept
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getRescaleIntercept(OFString &value,
-                                          const signed long pos = 0) const;
-
-  /** Get RescaleSlope
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getRescaleSlope(OFString &value,
-                                      const signed long pos = 0) const;
-
-  /** Get RescaleType
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getRescaleType(OFString &value,
-                                     const signed long pos = 0) const;
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGUnknown) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the this object, or all compared components match
-   *          but this component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in this object, or all compared components match
-   *          but this component is longer.
-   */
-  virtual int compare(const FGBase& rhs) const;
-
-  /** Set RescaleIntercept
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRescaleIntercept(const OFString &value,
-                                          const OFBool checkValue = OFTrue);
-
-  /** Set RescaleSlope
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRescaleSlope(const OFString &value,
-                                      const OFBool checkValue = OFTrue);
-
-  /** Set RescaleType
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRescaleType(const OFString &value,
-                                     const OFBool checkValue = OFTrue);
+    /** Destructor, frees memory
+     */
+    virtual ~FGPixelValueTransformation();
+
+    /** This method is deprecated, use setFGType instead.
+     *
+     * Tell this class that it should behave like the Identity Pixel Value
+     *  Transformation Functional Group. This does not make a difference when
+     *  reading data, but when writing, it is assured that Rescale Slope,
+     *  Intercept and Type are forced to be set to 1, 0 and "US" respectively.
+     */
+    virtual void setUseAsIdentityPixelValueTransformation();
+
+    /** Tell this class as which type of functional group it should behave.
+     *  Transformation Functional Group. This does not make a difference when
+     *  reading or writing data, but the component name is written correctly
+     *  for all corresponding log messages.
+     *  @param  fgType Denotes which Functional Group Macro should be represented
+     *          by this class.
+     */
+    virtual void setFGType(const E_PixelValueTransformationSubType fgType);
+
+    /** Get type Functional Group represented by this class.
+     *  @return Type of functional group represented by this class
+     */
+    virtual E_PixelValueTransformationSubType getFGType() const;
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Get shared type of this functional group (can be both, per-frame and
+     *  shared)
+     *  @return Always returns EFGS_BOTH
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clears all data
+     */
+    virtual void clearData();
+
+    /** Check whether functional group contains valid data
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read functional group from given item, i.e.\ read (Identity) Pixel Value
+     *  Transformation Sequence. Clears existing data before reading.
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Write functional group to given item, i.e.\ write (Identity) Pixel Value
+     *  Transformation Sequence
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Get RescaleIntercept
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getRescaleIntercept(OFString& value, const signed long pos = 0) const;
+
+    /** Get RescaleSlope
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getRescaleSlope(OFString& value, const signed long pos = 0) const;
+
+    /** Get RescaleType
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getRescaleType(OFString& value, const signed long pos = 0) const;
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    /** Set RescaleIntercept
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setRescaleIntercept(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set RescaleSlope
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setRescaleSlope(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set RescaleType
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setRescaleType(const OFString& value, const OFBool checkValue = OFTrue);
+
+protected:
+    /** Returns String denoting the type of functional group represented by this class
+     *  @return String denoting the type of functional group
+     */
+    virtual OFString fgType2Str();
 
 private:
-
-  /* Content of Identity Pixel Value Transformation Functional Group Macro */
-
-  /// RescaleIntercept (DS, VM 1, Required type 1)
-  DcmDecimalString m_RescaleIntercept;
-
-  /// RescaleSlope (DS, VM 1, Required type 1)
-  DcmDecimalString m_RescaleSlope;
-
-  /// RescaleType (LO, VM 1, Required type 1)
-  DcmLongString m_RescaleType;
-
-  /// If OFTrue, tells this class that it should behave like the Identity Pixel
-  /// Value Transformation Functional Group. This does not make a difference when
-  /// reading data, but when writing, it is assured that Rescale Slope,
-  /// Intercept and Type are forced to be set to 1, 0 and "US" respectively.
-  OFBool m_UseAsIdentityPixelValueTransformationFG;
+    /* Content of Identity Pixel Value Transformation Functional Group Macro */
+
+    /// RescaleIntercept (DS, VM 1, Required type 1)
+    DcmDecimalString m_RescaleIntercept;
+
+    /// RescaleSlope (DS, VM 1, Required type 1)
+    DcmDecimalString m_RescaleSlope;
+
+    /// RescaleType (LO, VM 1, Required type 1)
+    DcmLongString m_RescaleType;
+
+    /// Denotes the represented functional group type.
+    ///
+    /// E_PixelValTrans_Normal: Normal Pixel Value Transformation FG.
+    ///   No no special value requirements.
+    /// E_PixelValTrans_Identity: Identity Pixel Value Transformation FG.
+    ///   Tells this class that it should behave like the Identity Pixel
+    ///   Value Transformation FG. This does not make a difference when
+    ///   reading data, but when writing, it is assured that Rescale Slope,
+    ///   Intercept and Type are forced to be set to 1, 0 and "US" respectively.
+    /// E_PixelValTrans_CT: CT Pixel Value Transformation FG.
+    ///   Tells this class that it should behave like the CT Pixel
+    ///   Value Transformation FG. No special value requirements.
+    E_PixelValueTransformationSubType m_fgSubType;
 };
 
 #endif // FGPIXELTRANSFORM_H
index 72f43f121e9a92d580e254a6bcdc280aa441e64a..f2a053eb716db9ef6aa74c5bfe7eebcf01df302d 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -23,6 +23,7 @@
 #define FGPIXMSR_H
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcitem.h"
 #include "dcmtk/dcmdata/dcvrds.h"
 #include "dcmtk/dcmfg/fgbase.h"
 class DCMTK_DCMFG_EXPORT FGPixelMeasures : public FGBase
 {
 public:
-
-  /** Constructor, creates empty Pixel Measures Functional Group
-   */
-  FGPixelMeasures();
-
-  /** Virtual destructor, frees memory
-   */
-  virtual ~FGPixelMeasures();
-
-  /** Returns a deep copy of this object
-   *  @return Deep copy of this object
-   */
-  virtual FGBase *clone() const;
-
-
-  /** Returns shared type of this group (can be shared or per-frame)
-   *  @return Always returns DcmFGTypes::EFGS_BOTH;
-   */
-  virtual DcmFGTypes::E_FGSharedType getSharedType() const {return DcmFGTypes::EFGS_BOTH;}
-
-  /** Clear all data
-   */
-  virtual void clearData();
-
-  /** Check whether data in functional group is valid
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  virtual OFCondition check() const;
-
-  /** Read functional group from given item
-   *  @param  item The item to read from, must contain Pixel Measures Sequence
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& item);
-
-  /** Write functional group to given item
-   *  @param  item The item to write Pixel Measures Sequence to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
-
-  // --- get() functionality ---
-
-  /** Get Pixel Spacing
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getPixelSpacing(Float64& value,
-                                      const signed long pos = 0);
-
-  /** Get Slice Thickness
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getSliceThickness(Float64& value,
-                                        const signed long pos = 0);
-
-  /** Get Spacing Between Slices
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getSpacingBetweenSlices(Float64& value,
-                                              const signed long pos = 0);
-
-  // --- set() functionality ---
-
-  /** Set Pixel Spacing
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (2) if
-   *          enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPixelSpacing(const OFString& value,
-                                      const OFBool checkValue = OFTrue);
-
-  /** Set Slice Thickness
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1) if
-   *          enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSliceThickness(const OFString& value,
-                                        const OFBool checkValue = OFTrue);
-
-  /** Set Spacing between Slices
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1) if
-   *          enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSpacingBetweenSlices(const OFString& value,
-                                              const OFBool checkValue = OFTrue);
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGUnknown) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the this object, or all compared components match
-   *          but this component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in this object, or all compared components match
-   *          but this component is longer.
-   */
-  virtual int compare(const FGBase& rhs) const;
+    /** Constructor, creates empty Pixel Measures Functional Group
+     */
+    FGPixelMeasures();
+
+    /** Virtual destructor, frees memory
+     */
+    virtual ~FGPixelMeasures();
+
+    /** Returns a deep copy of this object
+     *  @return Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Returns shared type of this group (can be shared or per-frame)
+     *  @return Always returns DcmFGTypes::EFGS_BOTH;
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clear all data
+     */
+    virtual void clearData();
+
+    /** Check whether data in functional group is valid
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read functional group from given item
+     *  @param  item The item to read from, must contain Pixel Measures Sequence
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Write functional group to given item
+     *  @param  item The item to write Pixel Measures Sequence to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    // --- get() functionality ---
+
+    /** Get Pixel Spacing
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPixelSpacing(Float64& value, const unsigned long pos = 0);
+
+    /** Get Slice Thickness
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSliceThickness(Float64& value, const unsigned long pos = 0);
+
+    /** Get Spacing Between Slices
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSpacingBetweenSlices(Float64& value, const unsigned long pos = 0);
+
+    // --- set() functionality ---
+
+    /** Set Pixel Spacing
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (2) if
+     *          enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPixelSpacing(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Slice Thickness
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1) if
+     *          enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSliceThickness(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Spacing between Slices
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1) if
+     *          enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSpacingBetweenSlices(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
 
 private:
+    /* Content of Pixel Measures Macro */
 
-  /* Content of Pixel Measures Macro */
-
-  /// Pixel Spacing   (DS, VM 2, Required type 1C)
-  DcmDecimalString m_PixelSpacing;
+    /// Pixel Spacing   (DS, VM 2, Required type 1C)
+    DcmDecimalString m_PixelSpacing;
 
-  /// Slice Thickness (DS, VM 1, Required type 1C)
-  DcmDecimalString m_SliceThickness;
+    /// Slice Thickness (DS, VM 1, Required type 1C)
+    DcmDecimalString m_SliceThickness;
 
-  /// Spacing Between Slices (DS, VM 1, Required type 3)
-  DcmDecimalString m_SpacingBetweenSlices;
+    /// Spacing Between Slices (DS, VM 1, Required type 3)
+    DcmDecimalString m_SpacingBetweenSlices;
 };
 
 #endif // FGPIXMSRS_H
index 2b8de1920677874e3cba9efb998ceab8bbb54783..6ffb3df059e55972d7e7c0ad56e832e945ad3929 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define FGPLANOR_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmfg/fgbase.h"
+
 #include "dcmtk/dcmdata/dcsequen.h"
 #include "dcmtk/dcmdata/dcvrds.h"
+#include "dcmtk/dcmfg/fgbase.h"
 
 /** Class representing the Plane Orientation (Patient) Functional Group Macro.
  *  It specifies the direction cosines of the first row and the first column
 class DCMTK_DCMFG_EXPORT FGPlaneOrientationPatient : public FGBase
 {
 public:
-
-  /** Constructor, creates empty functional group
-   */
-  FGPlaneOrientationPatient();
-
-  /** Destructor, frees memory
-   */
-  virtual ~FGPlaneOrientationPatient();
-
-  /** Returns a deep copy of this object
-   *  @return  Deep copy of this object
-   */
-  virtual FGBase *clone() const;
-
-  /** Convenience function to create a minimal functional group.
-   *  @param  imageOrientationPatientRowX Row X Value
-   *  @param  imageOrientationPatientRowY Row Y Value
-   *  @param  imageOrientationPatientRowZ Row Z Value
-   *  @param  imageOrientationPatientColX Column X Value
-   *  @param  imageOrientationPatientColY Column Y Value
-   *  @param  imageOrientationPatientColZ Column Z Value
-   *  @return The functional group created with above parameters
-   */
-  static FGPlaneOrientationPatient* createMinimal(const OFString& imageOrientationPatientRowX,
-                                                  const OFString& imageOrientationPatientRowY,
-                                                  const OFString& imageOrientationPatientRowZ,
-                                                  const OFString& imageOrientationPatientColX,
-                                                  const OFString& imageOrientationPatientColY,
-                                                  const OFString& imageOrientationPatientColZ);
-
-  /** Get shared type of this functional group (can be both, shared and
-   *  per-frame)
-   *  @return Always returns DcmFGTypes::EFGS_BOTH
-   */
-  virtual DcmFGTypes::E_FGSharedType getSharedType() const {return DcmFGTypes::EFGS_BOTH;}
-
-  /** Clears all data
-   */
-  virtual void clearData();
-
-  /** Check whether this group contains valid data
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  virtual OFCondition check() const;
-
-  /** Read functional group from item, must contain the Plane Orientation
-   *  Sequence
-   *  @param  item The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& item);
-
-  /** Writes functional group to given item (will write Plane Orientation
-   *  Sequence to it)
-   *  @param  item The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGUnknown) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the this object, or all compared components match
-   *          but this component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in this object, or all compared components match
-   *          but this component is longer.
-   */
-  virtual int compare(const FGBase& rhs) const;
-
-  // --- get() functionality ---
-
-  /** Get Image Orientation Patient
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getImageOrientationPatient(OFString& value,
-                                                 const signed long pos);
-
-  /** Retrieve all values of Image Orientation Patient at the same time
-   *  @param  rowX Row X Value
-   *  @param  rowY Row Y Value
-   *  @param  rowZ Row Z Value
-   *  @param  colX Column X Value
-   *  @param  colY Column Y Value
-   *  @param  colZ Column Z Value
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getImageOrientationPatient(Float64& rowX,
-                                                 Float64& rowY,
-                                                 Float64& rowZ,
-                                                 Float64& colX,
-                                                 Float64& colY,
-                                                 Float64& colZ);
-
-  // --- set() functionality ---
-
-   /** Set all values of Image Orientation Patient at once
-    *  @param  rowX Row X Value
-    *  @param  rowY Row Y Value
-    *  @param  rowZ Row Z Value
-    *  @param  colX Column X Value
-    *  @param  colY Column Y Value
-    *  @param  colZ Column Z Value
-    *  @param  checkValue If OFTrue, values are checked for validity
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition setImageOrientationPatient(const OFString& rowX,
-                                                 const OFString& rowY,
-                                                 const OFString& rowZ,
-                                                 const OFString& colX,
-                                                 const OFString& colY,
-                                                 const OFString& colZ,
-                                                 const OFBool checkValue = OFTrue);
+    /** Constructor, creates empty functional group
+     */
+    FGPlaneOrientationPatient();
+
+    /** Destructor, frees memory
+     */
+    virtual ~FGPlaneOrientationPatient();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Convenience function to create a minimal functional group.
+     *  @param  imageOrientationPatientRowX Row X Value
+     *  @param  imageOrientationPatientRowY Row Y Value
+     *  @param  imageOrientationPatientRowZ Row Z Value
+     *  @param  imageOrientationPatientColX Column X Value
+     *  @param  imageOrientationPatientColY Column Y Value
+     *  @param  imageOrientationPatientColZ Column Z Value
+     *  @return The functional group created with above parameters
+     */
+    static FGPlaneOrientationPatient* createMinimal(const OFString& imageOrientationPatientRowX,
+                                                    const OFString& imageOrientationPatientRowY,
+                                                    const OFString& imageOrientationPatientRowZ,
+                                                    const OFString& imageOrientationPatientColX,
+                                                    const OFString& imageOrientationPatientColY,
+                                                    const OFString& imageOrientationPatientColZ);
+
+    /** Get shared type of this functional group (can be both, shared and
+     *  per-frame)
+     *  @return Always returns DcmFGTypes::EFGS_BOTH
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clears all data
+     */
+    virtual void clearData();
+
+    /** Check whether this group contains valid data
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read functional group from item, must contain the Plane Orientation
+     *  Sequence
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Writes functional group to given item (will write Plane Orientation
+     *  Sequence to it)
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    // --- get() functionality ---
+
+    /** Get Image Orientation Patient
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getImageOrientationPatient(OFString& value, const signed long pos);
+
+    /** Retrieve all values of Image Orientation Patient at the same time
+     *  @param  rowX Row X Value
+     *  @param  rowY Row Y Value
+     *  @param  rowZ Row Z Value
+     *  @param  colX Column X Value
+     *  @param  colY Column Y Value
+     *  @param  colZ Column Z Value
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getImageOrientationPatient(
+        Float64& rowX, Float64& rowY, Float64& rowZ, Float64& colX, Float64& colY, Float64& colZ);
+
+    // --- set() functionality ---
+
+    /** Set all values of Image Orientation Patient at once
+     *  @param  rowX Row X Value
+     *  @param  rowY Row Y Value
+     *  @param  rowZ Row Z Value
+     *  @param  colX Column X Value
+     *  @param  colY Column Y Value
+     *  @param  colZ Column Z Value
+     *  @param  checkValue If OFTrue, values are checked for validity
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setImageOrientationPatient(const OFString& rowX,
+                                                   const OFString& rowY,
+                                                   const OFString& rowZ,
+                                                   const OFString& colX,
+                                                   const OFString& colY,
+                                                   const OFString& colZ,
+                                                   const OFBool checkValue = OFTrue);
 
 private:
+    /* Content of Plane Orientation (Patient) Macro */
 
-  /* Content of Plane Orientation (Patient) Macro */
-
-  /// Image Orientation (Patient)   (DS, VM 6, Required type 1C)
-  DcmDecimalString m_ImageOrientationPatient;
+    /// Image Orientation (Patient)   (DS, VM 6, Required type 1C)
+    DcmDecimalString m_ImageOrientationPatient;
 };
 
 #endif // FGPLANOR_H
index 16729c946fabfd40a77502d2303394c18f50c416..73ad23d5622c66b8240a38076afa3dba3865eb9a 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -23,6 +23,7 @@
 #define FGPLANORVOL_H
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcitem.h"
 #include "dcmtk/dcmfg/fgbase.h"
 
 class DCMTK_DCMFG_EXPORT FGPlaneOrientationVolume : public FGBase
 {
 public:
-
-  /** Constructor, creates empty Plane Orientation (Volume) Functional Group
-   */
-  FGPlaneOrientationVolume();
-
-  /** Destructor, frees memory
-   */
-  virtual ~FGPlaneOrientationVolume();
-
-  /** Returns a deep copy of this object
-   *  @return  Deep copy of this object
-   */
-  virtual FGBase *clone() const;
-
-  /** Get shared type of this functional group (can be both, per-frame and
-   *  shared)
-   *  @return Always returns DcmFGTypes::EFGS_BOTH
-   */
-  virtual DcmFGTypes::E_FGSharedType getSharedType() const {return DcmFGTypes::EFGS_BOTH;}
-
-  /** Clears all data
-   */
-  virtual void clearData();
-
-  /** Check whether functional group contains valid data
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  virtual OFCondition check() const;
-
-  /** Read functional group from given item, i.e.\ read Plane Orientation
-   *  (Volume) Sequence
-   *  @param  item The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& item);
-
-  /** Write functional group to given item, i.e.\ write Plane Orientation
-   *  (Volume) Sequence
-   *  @param  item The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
-
-  // --- get() functionality ---
-
-  /** Get Image Orientation Volume
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getImageOrientationVolume(Float64& value,
-                                                const unsigned long pos = 0);
-
-  /** Retrieve all values of Image Orientation Volume at the same time
-   *  @param  rowX Row X Value
-   *  @param  rowY Row Y Value
-   *  @param  rowZ Row Z Value
-   *  @param  colX Column X Value
-   *  @param  colY Column Y Value
-   *  @param  colZ Column Z Value
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getImageOrientationVolume(Float64& rowX,
-                                                Float64& rowY,
-                                                Float64& rowZ,
-                                                Float64& colX,
-                                                Float64& colY,
-                                                Float64& colZ);
-
-  // --- set() functionality ---
-
-   /** Set all values of Image Orientation Volume at once
-    *  @param  rowX Row X Value
-    *  @param  rowY Row Y Value
-    *  @param  rowZ Row Z Value
-    *  @param  colX Column X Value
-    *  @param  colY Column Y Value
-    *  @param  colZ Column Z Value
-    *  @param  checkValue If OFTrue, values are checked for validity (not
-    *          implemented yet)
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition setImageOrientationVolume(const Float64& rowX,
-                                                const Float64& rowY,
-                                                const Float64& rowZ,
-                                                const Float64& colX,
-                                                const Float64& colY,
-                                                const Float64& colZ,
-                                                const OFBool checkValue = OFTrue);
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGUnknown) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the this object, or all compared components match
-   *          but this component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in this object, or all compared components match
-   *          but this component is longer.
-   */
-  virtual int compare(const FGBase& rhs) const;
+    /** Constructor, creates empty Plane Orientation (Volume) Functional Group
+     */
+    FGPlaneOrientationVolume();
+
+    /** Destructor, frees memory
+     */
+    virtual ~FGPlaneOrientationVolume();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Get shared type of this functional group (can be both, per-frame and
+     *  shared)
+     *  @return Always returns DcmFGTypes::EFGS_BOTH
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clears all data
+     */
+    virtual void clearData();
+
+    /** Check whether functional group contains valid data
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read functional group from given item, i.e.\ read Plane Orientation
+     *  (Volume) Sequence
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Write functional group to given item, i.e.\ write Plane Orientation
+     *  (Volume) Sequence
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    // --- get() functionality ---
+
+    /** Get Image Orientation Volume
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getImageOrientationVolume(Float64& value, const unsigned long pos = 0);
+
+    /** Retrieve all values of Image Orientation Volume at the same time
+     *  @param  rowX Row X Value
+     *  @param  rowY Row Y Value
+     *  @param  rowZ Row Z Value
+     *  @param  colX Column X Value
+     *  @param  colY Column Y Value
+     *  @param  colZ Column Z Value
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition
+    getImageOrientationVolume(Float64& rowX, Float64& rowY, Float64& rowZ, Float64& colX, Float64& colY, Float64& colZ);
+
+    // --- set() functionality ---
+
+    /** Set all values of Image Orientation Volume at once
+     *  @param  rowX Row X Value
+     *  @param  rowY Row Y Value
+     *  @param  rowZ Row Z Value
+     *  @param  colX Column X Value
+     *  @param  colY Column Y Value
+     *  @param  colZ Column Z Value
+     *  @param  checkValue If OFTrue, values are checked for validity (not
+     *          implemented yet)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setImageOrientationVolume(const Float64& rowX,
+                                                  const Float64& rowY,
+                                                  const Float64& rowZ,
+                                                  const Float64& colX,
+                                                  const Float64& colY,
+                                                  const Float64& colZ,
+                                                  const OFBool checkValue = OFTrue);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
 
 private:
+    /* Content of Plane Orientation (Volume) Macro */
 
-  /* Content of Plane Orientation (Volume) Macro */
-
-  /// Image Orientation (Volume) (FD, VM 6, Required type 1)
-  DcmFloatingPointDouble m_ImageOrientationVolume;
+    /// Image Orientation (Volume) (FD, VM 6, Required type 1)
+    DcmFloatingPointDouble m_ImageOrientationVolume;
 };
 
 #endif // FGPLANORVOL_H
index 1fcf2a21225737c034613b6aa779863749ea2030..c2557d6009d32887dd9d4388a7f15722ed9204b6 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define FGPLANPO_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmfg/fgbase.h"
+
 #include "dcmtk/dcmdata/dcsequen.h"
 #include "dcmtk/dcmdata/dcvrds.h"
+#include "dcmtk/dcmfg/fgbase.h"
 
 /** Class representing the Plane Position (Patient) Functional Group containing
  *  the x, y, and z coordinates of the upper left hand corner (center of the
 class DCMTK_DCMFG_EXPORT FGPlanePosPatient : public FGBase
 {
 public:
-
-  /** Constructor, creates empty functional group
-   */
-  FGPlanePosPatient();
-
-  /** Destructor, frees memory
-   */
-  virtual ~FGPlanePosPatient();
-
-  /** Returns a deep copy of this object
-   *  @return  Deep copy of this object
-   */
-  virtual FGBase *clone() const;
-
-  /** Convenience function to create minimal functional group
-   *  @param  imagePositionPatientX The X coordinate of the upper left hand
-   *          corner of the the frame in mm.
-   *  @param  imagePositionPatientY The Y coordinate of the upper left hand
-   *          corner of the the frame in mm.
-   *  @param  imagePositionPatientZ The Z coordinate of the upper left hand
-   *          corner of the the frame in mm.
-   */
-  static FGPlanePosPatient* createMinimal(const OFString& imagePositionPatientX,
-                                          const OFString& imagePositionPatientY,
-                                          const OFString& imagePositionPatientZ);
-
-  /** Returns that this functional group can be shared or per-frame (both)
-   *  @return Always returns DcmFGTypes::EFGS_BOTH
-   */
-  virtual DcmFGTypes::E_FGSharedType getSharedType() const {return DcmFGTypes::EFGS_BOTH;}
-
-  /** Clears all data
-   */
-  virtual void clearData();
-
-  /** Check whether data in functional group is valid
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  virtual OFCondition check() const;
-
-  /** Read functional group from item, must contain the Plane Position Sequence
-   *  @param  item The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& item);
-
-  /** Write functional group to item, will write the Plane Position Sequence
-   *  @param  item The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGUnknown) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the this object, or all compared components match
-   *          but this component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in this object, or all compared components match
-   *          but this component is longer.
-   */
-  virtual int compare(const FGBase& rhs) const;
-
-  // --- get() functionality ---
-
-  /** Get Image Position Patient
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getImagePositionPatient(OFString& value,
-                                              const signed long pos);
-
-  /** Retrieve all values of Image Orientation Patient at the same time
-   *  @param  coordinateX X coordinate of upper left hand corner voxel in mm
-   *  @param  coordinateY Y coordinate of upper left hand corner voxel in mm
-   *  @param  coordinateZ Z coordinate of upper left hand corner voxel in mm
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getImagePositionPatient(Float64& coordinateX,
-                                              Float64& coordinateY,
-                                              Float64& coordinateZ);
-
-  // --- set() functionality ---
-
-  /** Set Image Position Patient. The x, y, and z coordinates of the upper left
-   *  hand corner (center of the first voxel transmitted) of the frame, in mm.
-   *  @param  coordinateX X coordinate of upper left hand corner voxel in mm
-   *  @param  coordinateY Y coordinate of upper left hand corner voxel in mm
-   *  @param  coordinateZ Z coordinate of upper left hand corner voxel in mm
-   *  @param  checkValue Check coordinates for validity, including VR (DS)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setImagePositionPatient(const OFString& coordinateX,
-                                              const OFString& coordinateY,
-                                              const OFString& coordinateZ,
-                                              const OFBool checkValue = OFTrue);
+    /** Constructor, creates empty functional group
+     */
+    FGPlanePosPatient();
+
+    /** Destructor, frees memory
+     */
+    virtual ~FGPlanePosPatient();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Convenience function to create minimal functional group
+     *  @param  imagePositionPatientX The X coordinate of the upper left hand
+     *          corner of the the frame in mm.
+     *  @param  imagePositionPatientY The Y coordinate of the upper left hand
+     *          corner of the the frame in mm.
+     *  @param  imagePositionPatientZ The Z coordinate of the upper left hand
+     *          corner of the the frame in mm.
+     *  @return Newly created Plane Position Functional Group or NULL in case of error
+     */
+    static FGPlanePosPatient* createMinimal(const OFString& imagePositionPatientX,
+                                            const OFString& imagePositionPatientY,
+                                            const OFString& imagePositionPatientZ);
+
+    /** Returns that this functional group can be shared or per-frame (both)
+     *  @return Always returns DcmFGTypes::EFGS_BOTH
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clears all data
+     */
+    virtual void clearData();
+
+    /** Check whether data in functional group is valid
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read functional group from item, must contain the Plane Position Sequence
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Write functional group to item, will write the Plane Position Sequence
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    // --- get() functionality ---
+
+    /** Get Image Position Patient
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getImagePositionPatient(OFString& value, const signed long pos);
+
+    /** Retrieve all values of Image Orientation Patient at the same time
+     *  @param  coordinateX X coordinate of upper left hand corner voxel in mm
+     *  @param  coordinateY Y coordinate of upper left hand corner voxel in mm
+     *  @param  coordinateZ Z coordinate of upper left hand corner voxel in mm
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getImagePositionPatient(Float64& coordinateX, Float64& coordinateY, Float64& coordinateZ);
+
+    // --- set() functionality ---
+
+    /** Set Image Position Patient. The x, y, and z coordinates of the upper left
+     *  hand corner (center of the first voxel transmitted) of the frame, in mm.
+     *  @param  coordinateX X coordinate of upper left hand corner voxel in mm
+     *  @param  coordinateY Y coordinate of upper left hand corner voxel in mm
+     *  @param  coordinateZ Z coordinate of upper left hand corner voxel in mm
+     *  @param  checkValue Check coordinates for validity, including VR (DS)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setImagePositionPatient(const OFString& coordinateX,
+                                                const OFString& coordinateY,
+                                                const OFString& coordinateZ,
+                                                const OFBool checkValue = OFTrue);
 
 private:
+    /* Content of Plane Position Patient Macro */
 
-  /* Content of Plane Position Patient Macro */
-
-  /// Image Position (Patient)   (DS, VM 3, Required type 1C)
-  DcmDecimalString m_ImagePositionPatient;
+    /// Image Position (Patient)   (DS, VM 3, Required type 1C)
+    DcmDecimalString m_ImagePositionPatient;
 };
 
 #endif // FGPLANPO_H
index 40086ca84ed26c960df0e2b7fbe5c6e5f524a42e..037fb12546a969c7545310bb2cb7531aafc34936 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -23,6 +23,7 @@
 #define FGPLANEPOSVOL_H
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcitem.h"
 #include "dcmtk/dcmfg/fgbase.h"
 
 class DCMTK_DCMFG_EXPORT FGPlanePositionVolume : public FGBase
 {
 public:
-
-  /** Constructor, creates empty functional group
-   */
-  FGPlanePositionVolume();
-
-  /** Virtual destructor, frees memory
-   */
-  virtual ~FGPlanePositionVolume();
-
-  /** Returns a deep copy of this object
-   *  @return  Deep copy of this object
-   */
-  virtual FGBase *clone() const;
-
-  /** Returns shared type of this functional group (can be shared or per-frame,
-   *  i.e.\ both)
-   *  @return Always returns DcmFGTypes::EFGS_BOTH
-   */
-  virtual DcmFGTypes::E_FGSharedType getSharedType() const {return DcmFGTypes::EFGS_BOTH;}
-
-  /** Clears all data
-   */
-  virtual void clearData();
-
-  /** Check whether data of this functional group is valid
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  virtual OFCondition check() const;
-
-  /** Read functional group from item, must contain the Plane Position (Volume)
-   *  Sequence
-   *  @param  item The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& item);
-
-  /** Writes functional group to item, i.e.\ writes the Plane Position (Volume)
-   *  Sequence
-   *  @param  item The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
-
-  // --- get() functionality ---
-
-  /** Get Image Position Volume
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getImagePositionVolume(Float64& value,
-                                             const unsigned long pos = 0);
-
-  /** Retrieve all values of Image Position Volume at the same time
-   *  @param  valueX X coordinate of upper left hand corner voxel in mm
-   *  @param  valueY Y coordinate of upper left hand corner voxel in mm
-   *  @param  valueZ Z coordinate of upper left hand corner voxel in mm
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getImagePositionVolume(Float64& valueX,
-                                             Float64& valueY,
-                                             Float64& valueZ);
-
-  // --- set() functionality ---
-
-  /** Set Image Position Volume, i.e.\ the x/y/z coordinates of the upper left
-   *  hand corner (center of the first voxel transmitted) of the frame, in mm.
-   *  @param  value X,Y or Z coordinate of upper left hand corner voxel in mm
-   *  @param  pos pos 0 is x, pos 1 is Y, pos 2 addresses Z coordinate
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setImagePositionVolume(const Float64& value,
-                                             const unsigned long pos = 0,
-                                             const OFBool checkValue = OFTrue);
-
-  /** Set Image Position Volume, i.e.\ the x/y/z coordinates of the upper left
-   *  hand corner (center of the first voxel transmitted) of the frame, in mm.
-   *  @param  valueX X coordinate of upper left hand corner voxel in mm
-   *  @param  valueY coordinate of upper left hand corner voxel in mm
-   *  @param  valueZ coordinate of upper left hand corner voxel in mm
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setImagePositionVolume(const Float64& valueX,
-                                             const Float64& valueY,
-                                             const Float64& valueZ,
-                                             const OFBool checkValue = OFTrue);
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGUnknown) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the this object, or all compared components match
-   *          but this component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in this object, or all compared components match
-   *          but this component is longer.
-   */
-  virtual int compare(const FGBase& rhs) const;
+    /** Constructor, creates empty functional group
+     */
+    FGPlanePositionVolume();
+
+    /** Virtual destructor, frees memory
+     */
+    virtual ~FGPlanePositionVolume();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Returns shared type of this functional group (can be shared or per-frame,
+     *  i.e.\ both)
+     *  @return Always returns DcmFGTypes::EFGS_BOTH
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clears all data
+     */
+    virtual void clearData();
+
+    /** Check whether data of this functional group is valid
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read functional group from item, must contain the Plane Position (Volume)
+     *  Sequence
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Writes functional group to item, i.e.\ writes the Plane Position (Volume)
+     *  Sequence
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    // --- get() functionality ---
+
+    /** Get Image Position Volume
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getImagePositionVolume(Float64& value, const unsigned long pos = 0);
+
+    /** Retrieve all values of Image Position Volume at the same time
+     *  @param  valueX X coordinate of upper left hand corner voxel in mm
+     *  @param  valueY Y coordinate of upper left hand corner voxel in mm
+     *  @param  valueZ Z coordinate of upper left hand corner voxel in mm
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getImagePositionVolume(Float64& valueX, Float64& valueY, Float64& valueZ);
+
+    // --- set() functionality ---
+
+    /** Set Image Position Volume, i.e.\ the x/y/z coordinates of the upper left
+     *  hand corner (center of the first voxel transmitted) of the frame, in mm.
+     *  @param  value X,Y or Z coordinate of upper left hand corner voxel in mm
+     *  @param  pos pos 0 is x, pos 1 is Y, pos 2 addresses Z coordinate
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition
+    setImagePositionVolume(const Float64& value, const unsigned long pos = 0, const OFBool checkValue = OFTrue);
+
+    /** Set Image Position Volume, i.e.\ the x/y/z coordinates of the upper left
+     *  hand corner (center of the first voxel transmitted) of the frame, in mm.
+     *  @param  valueX X coordinate of upper left hand corner voxel in mm
+     *  @param  valueY coordinate of upper left hand corner voxel in mm
+     *  @param  valueZ coordinate of upper left hand corner voxel in mm
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setImagePositionVolume(const Float64& valueX,
+                                               const Float64& valueY,
+                                               const Float64& valueZ,
+                                               const OFBool checkValue = OFTrue);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
 
 private:
+    /* Content of Plane Position (Volume) Macro */
 
-  /* Content of Plane Position (Volume) Macro */
-
-  /// Image Position (Volume) (FD, VM 3, Required type 1)
-  DcmFloatingPointDouble m_ImagePositionVolume;
+    /// Image Position (Volume) (FD, VM 3, Required type 1)
+    DcmFloatingPointDouble m_ImagePositionVolume;
 };
 
 #endif // FGPLANEPOSVOL_H
index 27545f9f0114b77f582f76cd0e40e3380713d1ea..c734364f41d17c9cceb0a8f3c81a4bb7fcbaa440 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2017, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define FGREALWORLDVALUEMAPPING_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmfg/fgbase.h"
+
 #include "dcmtk/dcmdata/dcitem.h"
-#include "dcmtk/dcmiod/modbase.h"
-#include "dcmtk/dcmiod/iodmacro.h"
+#include "dcmtk/dcmfg/fgbase.h"
 #include "dcmtk/dcmiod/iodcontentitemmacro.h"
+#include "dcmtk/dcmiod/iodmacro.h"
+#include "dcmtk/dcmiod/modbase.h"
 
 /** Class representing the Real World Value Mapping Functional Group that
  *  specifies the mapping of stored values to associated Real World values
  */
-class DCMTK_DCMFG_EXPORT FGRealWorldValueMapping: public FGBase
+class DCMTK_DCMFG_EXPORT FGRealWorldValueMapping : public FGBase
 {
 public:
-
-  // Forward declaration
-  class RWVMItem;
-
-  /** Constructor, creates empty functional group
-   */
-  FGRealWorldValueMapping();
-
-  /** Destructor, frees memory
-   */
-  virtual ~FGRealWorldValueMapping();
-
-  /** Returns a deep copy of this object
-   *  @return  Deep copy of this object
-   */
-  virtual FGBase *clone() const;
-
-  /** Returns that this functional group can be used as both, shared
-   *  and per-frame
-   *  @returns Always returns DcmFGTypes::EFGS_BOTH
-   */
-  virtual DcmFGTypes::E_FGSharedType getSharedType() const {return DcmFGTypes::EFGS_BOTH;}
-
-  /** Clear all data
-   */
-  virtual void clearData();
-
-  /** Check whether data of functional group is valid
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  virtual OFCondition check() const;
-
-  /** Read functional group from item, must contain the Real World Value Mapping
-   *  Sequence
-   *  @param  item The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& item);
-
-  /** Writes this functional group to item, i.e.\ will write the Real World Value
-   *  Mapping Sequence
-   *  @param  item The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
-
-  // --- get() functionality ---
-
-  /** Return references to the various items inside the Real World Value Mapping
-   *  Sequence
-   *  @return Reference to Real World Value Mapping Sequence items
-   */
-  virtual OFVector< RWVMItem* >& getRealWorldValueMapping();
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGUnknown) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the this object, or all compared components match
-   *          but this component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in this object, or all compared components match
-   *          but this component is longer.
-   */
-  virtual int compare(const FGBase& rhs) const;
+    // Forward declaration
+    class RWVMItem;
+
+    /** Constructor, creates empty functional group
+     */
+    FGRealWorldValueMapping();
+
+    /** Destructor, frees memory
+     */
+    virtual ~FGRealWorldValueMapping();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Returns that this functional group can be used as both, shared
+     *  and per-frame
+     *  @returns Always returns DcmFGTypes::EFGS_BOTH
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clear all data
+     */
+    virtual void clearData();
+
+    /** Check whether data of functional group is valid
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read functional group from item, must contain the Real World Value Mapping
+     *  Sequence
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Writes this functional group to item, i.e.\ will write the Real World Value
+     *  Mapping Sequence
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    // --- get() functionality ---
+
+    /** Return references to the various items inside the Real World Value Mapping
+     *  Sequence
+     *  @return Reference to Real World Value Mapping Sequence items
+     */
+    virtual OFVector<RWVMItem*>& getRealWorldValueMapping();
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
 
 private:
+    /* Content of Real World Value Mapping Macro */
 
-  /* Content of Real World Value Mapping Macro */
-
-  /// Items (1-n) of Real World Value Mapping Sequence
-  OFVector<RWVMItem*> m_Items;
+    /// Items (1-n) of Real World Value Mapping Sequence
+    OFVector<RWVMItem*> m_Items;
 };
 
 /** Class representing the Real World Value Mapping Item Macro:
@@ -137,284 +139,259 @@ private:
 class DCMTK_DCMFG_EXPORT FGRealWorldValueMapping::RWVMItem : public IODComponent
 {
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   *  @param  parent The parent of the IOD component (NULL if none or unknown)
-   */
-  RWVMItem(OFshared_ptr<DcmItem> item,
-           OFshared_ptr<IODRules> rules,
-           IODComponent* parent = NULL);
-
-  /** Constructor
-   *  @param  parent The parent of the IOD component (NULL if none or unknown)
-   */
-  RWVMItem(IODComponent* parent = NULL);
-
-  /** Copy Constructor
-   *  @param  rhs The item to copy from
-   */
-  RWVMItem(const RWVMItem& rhs);
-
-  /** Clone this class (perform deep copy)
-   *  @return Clone of this class or NULL (e.g.\ if memory exhausted)
-   */
-  RWVMItem* clone();
-
-  /** Virtual destructor, frees memory
-   */
-  virtual ~RWVMItem();
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of component
-   *  @return Name of the module
-   */
-  virtual OFString getName() const;
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGUnknown) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the this object, or all compared components match
-   *          but this component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in this object, or all compared components match
-   *          but this component is longer.
-   */
-  virtual int compare(const IODComponent& rhs) const;
-
-  /** Read attributes from given item into this class
-   *  @param source  The source to read from
-   *  @param clearOldData If OFTrue, old data is cleared before reading.
-   *         Otherwise old data is overwritten (or amended)
-   *  @result EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write attributes from this class into given item
-   *  @param  destination The item to write to
-   *  @result EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& destination);
-
-  // --- get() functionality ---
-
-  /** Get Real World Value First Value Mapped
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getRealWorldValueFirstValueMapped(Sint32& value,
-                                                        const unsigned long pos = 0) const;
-
-  /** Get Real World Value First Value Mapped
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getRealWorldValueLastValueMapped(Sint32 &value,
-                                                       const unsigned long pos = 0) const;
-
-  /** Get Double Float Real World Value First Value Mapped
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getDoubleFloatRealWorldValueFirstValueMapped(Float64& value,
-                                                                   const unsigned long pos = 0) const;
-
-  /** Get Double Float Real World Value Last Value Mapped
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getDoubleFloatRealWorldValueLastValueMapped(Float64& value,
-                                                                   const unsigned long pos = 0) const;
-
-  /** Get Real World Value LUT Data
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getRealWorldValueLUTData(Float64 &value,
-                                               const unsigned long pos = 0) const;
-
-  /** Get Real World Value LUT Data
-   *  @param  values Reference to variable in which the values should be stored
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getRealWorldValueLUTData(OFVector<Float64>& values) const;
-
-  /** Get LUT Explanation
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getLUTExplanation(OFString &value,
-                                        const signed long pos = 0) const;
-
-  /** Get LUT Label
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getLUTLabel(OFString &value,
-                                  const signed long pos = 0) const;
-
-  /** Get Measurement Units Code Sequence (content)
-   *  @return Reference to Measurement Units Code
-   */
-  virtual CodeSequenceMacro& getMeasurementUnitsCode();
-
-  /** Get a reference to the entire ConceptNameCodeSequence, including items
-   *  exceeding the value multiplicity restriction of "1"
-   *  @return a reference to the entire ConceptNameCodeSequence
-   */
-  virtual OFVector<ContentItemMacro*>& getEntireQuantityDefinitionSequence();
-
-  // --- set() functionality ---
-
-  /** Set Real World Value First Value Mapped
-   *  @param  value Value to be set. If Pixel Representation is 0 (unsigned
-   *          pixel data) value  must be 0 < value < 2^16. Otherwise use
-   *          setRealWorldValueFirstValueMappedSigned().
-   *  @param  checkValue Check 'value' for conformance with VR (US and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRealWorldValueFirstValueMappedUnsigned(const Uint16 value,
-                                                                const OFBool checkValue = OFTrue);
-
-  /** Set Real World Value First Value Mapped
-   *  @param  value Value to be set. If Pixel Representation is -1 (signed
-   *          pixel data) value  must be -2^15  < value < 2^15-1. Otherwise use
-   *          setRealWorldValueFirstValueMappedUnsigned().
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRealWorldValueFirstValueMappedSigned(const Sint16 &value,
-                                                              const OFBool checkValue = OFTrue);
-
-  /** Set Real World Value Last Value Mapped
-   *  @param  value Value to be set. If Pixel Representation is 0 (unsigned
-   *          pixel data) value  must be 0 < value < 2^16. Otherwise use
-   *          setRealWorldValueLastValueMappedSigned().
-   *  @param  checkValue Check 'value' for conformance with VR (US and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRealWorldValueLastValueMappedUnsigned(const Uint16 value,
-                                                               const OFBool checkValue = OFTrue);
-
-  /** Set Real World Value Last Value Mapped
-   *  @param  value Value to be set. If Pixel Representation is -1 (signed
-   *          pixel data) value  must be -2^15  < value < 2^15-1. Otherwise use
-   *          setRealWorldValueLastValueMappedUnsigned().
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRealWorldValueLastValueMappedSigned(const Sint16 &value,
-                                                             const OFBool checkValue = OFTrue);
-
-  /** Set Double Float Real World Value First Value Mapped
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value'. Does nothing, only for consistency with
-   *          other set() functions.
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setDoubleFloatRealWorldValueFirstValueMapped(const Float64 value,
-                                                                  const OFBool checkValue = OFTrue);
-
-  /** Set Double Float Real World Value Last Value Mapped
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value'. Does nothing, only for consistency with
-   *          other set() functions.
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setDoubleFloatRealWorldValueLastValueMapped(const Float64 value,
-                                                                  const OFBool checkValue = OFTrue);
-
-  /** Set Real World Value Intercept
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRealWorldValueIntercept(const Float64 value,
-                                                 const OFBool checkValue = OFTrue);
-
-  /** Set Real World Value Slope
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRealWorldValueSlope(const Float64 value,
-                                             const OFBool checkValue = OFTrue);
-
-  /** Set Real World Value LUT Data
-   *  @param  value Values to be set
-   *  @param  checkValue Check 'value' for conformance with VR (FD) and VM (1-n) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRealWorldValueLUTData(const OFVector<Float64>& value,
-                                               const OFBool checkValue = OFTrue);
-
-  /** Set LUT Explanation
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setLUTExplanation(const OFString &value,
-                                        const OFBool checkValue = OFTrue);
-
-  /** Set LUT Label
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance with VR (SH) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setLUTLabel(const OFString &value,
-                                  const OFBool checkValue = OFTrue);
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     *  @param  parent The parent of the IOD component (NULL if none or unknown)
+     */
+    RWVMItem(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules, IODComponent* parent = NULL);
+
+    /** Constructor
+     *  @param  parent The parent of the IOD component (NULL if none or unknown)
+     */
+    RWVMItem(IODComponent* parent = NULL);
+
+    /** Copy Constructor
+     *  @param  rhs The item to copy from
+     */
+    RWVMItem(const RWVMItem& rhs);
+
+    /** Clone this class (perform deep copy)
+     *  @return Clone of this class or NULL (e.g.\ if memory exhausted)
+     */
+    RWVMItem* clone();
+
+    /** Virtual destructor, frees memory
+     */
+    virtual ~RWVMItem();
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of component
+     *  @return Name of the module
+     */
+    virtual OFString getName() const;
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const IODComponent& rhs) const;
+
+    /** Read attributes from given item into this class
+     *  @param source  The source to read from
+     *  @param clearOldData If OFTrue, old data is cleared before reading.
+     *         Otherwise old data is overwritten (or amended)
+     *  @result EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write attributes from this class into given item
+     *  @param  destination The item to write to
+     *  @result EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& destination);
+
+    // --- get() functionality ---
+
+    /** Get Real World Value First Value Mapped
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getRealWorldValueFirstValueMapped(Sint32& value, const unsigned long pos = 0) const;
+
+    /** Get Real World Value First Value Mapped
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getRealWorldValueLastValueMapped(Sint32& value, const unsigned long pos = 0) const;
+
+    /** Get Double Float Real World Value First Value Mapped
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getDoubleFloatRealWorldValueFirstValueMapped(Float64& value, const unsigned long pos = 0) const;
+
+    /** Get Double Float Real World Value Last Value Mapped
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getDoubleFloatRealWorldValueLastValueMapped(Float64& value, const unsigned long pos = 0) const;
+
+    /** Get Real World Value LUT Data
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getRealWorldValueLUTData(Float64& value, const unsigned long pos = 0) const;
+
+    /** Get Real World Value LUT Data
+     *  @param  values Reference to variable in which the values should be stored
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getRealWorldValueLUTData(OFVector<Float64>& values) const;
+
+    /** Get LUT Explanation
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getLUTExplanation(OFString& value, const signed long pos = 0) const;
+
+    /** Get LUT Label
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getLUTLabel(OFString& value, const signed long pos = 0) const;
+
+    /** Get Measurement Units Code Sequence (content)
+     *  @return Reference to Measurement Units Code
+     */
+    virtual CodeSequenceMacro& getMeasurementUnitsCode();
+
+    /** Get a reference to the entire ConceptNameCodeSequence, including items
+     *  exceeding the value multiplicity restriction of "1"
+     *  @return a reference to the entire ConceptNameCodeSequence
+     */
+    virtual OFVector<ContentItemMacro*>& getEntireQuantityDefinitionSequence();
+
+    // --- set() functionality ---
+
+    /** Set Real World Value First Value Mapped
+     *  @param  value Value to be set. If Pixel Representation is 0 (unsigned
+     *          pixel data) value  must be 0 < value < 2^16. Otherwise use
+     *          setRealWorldValueFirstValueMappedSigned().
+     *  @param  checkValue Check 'value' for conformance with VR (US and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setRealWorldValueFirstValueMappedUnsigned(const Uint16 value, const OFBool checkValue = OFTrue);
+
+    /** Set Real World Value First Value Mapped
+     *  @param  value Value to be set. If Pixel Representation is -1 (signed
+     *          pixel data) value  must be -2^15  < value < 2^15-1. Otherwise use
+     *          setRealWorldValueFirstValueMappedUnsigned().
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setRealWorldValueFirstValueMappedSigned(const Sint16& value, const OFBool checkValue = OFTrue);
+
+    /** Set Real World Value Last Value Mapped
+     *  @param  value Value to be set. If Pixel Representation is 0 (unsigned
+     *          pixel data) value  must be 0 < value < 2^16. Otherwise use
+     *          setRealWorldValueLastValueMappedSigned().
+     *  @param  checkValue Check 'value' for conformance with VR (US and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setRealWorldValueLastValueMappedUnsigned(const Uint16 value, const OFBool checkValue = OFTrue);
+
+    /** Set Real World Value Last Value Mapped
+     *  @param  value Value to be set. If Pixel Representation is -1 (signed
+     *          pixel data) value  must be -2^15  < value < 2^15-1. Otherwise use
+     *          setRealWorldValueLastValueMappedUnsigned().
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setRealWorldValueLastValueMappedSigned(const Sint16& value, const OFBool checkValue = OFTrue);
+
+    /** Set Double Float Real World Value First Value Mapped
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value'. Does nothing, only for consistency with
+     *          other set() functions.
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setDoubleFloatRealWorldValueFirstValueMapped(const Float64 value,
+                                                                     const OFBool checkValue = OFTrue);
+
+    /** Set Double Float Real World Value Last Value Mapped
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value'. Does nothing, only for consistency with
+     *          other set() functions.
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setDoubleFloatRealWorldValueLastValueMapped(const Float64 value,
+                                                                    const OFBool checkValue = OFTrue);
+
+    /** Set Real World Value Intercept
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setRealWorldValueIntercept(const Float64 value, const OFBool checkValue = OFTrue);
+
+    /** Set Real World Value Slope
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setRealWorldValueSlope(const Float64 value, const OFBool checkValue = OFTrue);
+
+    /** Set Real World Value LUT Data
+     *  @param  value Values to be set
+     *  @param  checkValue Check 'value' for conformance with VR (FD) and VM (1-n) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setRealWorldValueLUTData(const OFVector<Float64>& value, const OFBool checkValue = OFTrue);
+
+    /** Set LUT Explanation
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setLUTExplanation(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set LUT Label
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance with VR (SH) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setLUTLabel(const OFString& value, const OFBool checkValue = OFTrue);
 
 protected:
-
-  static OFCondition getUSorSS(DcmItem& item,
-                               const DcmTagKey& key,
-                               const unsigned long pos,
-                               Sint32& value);
+    static OFCondition getUSorSS(DcmItem& item, const DcmTagKey& key, const unsigned long pos, Sint32& value);
 
 private:
+    /// The name of this module ("RealWorldValueMappingItemMacro")
+    static const OFString m_ModuleName;
 
-  /// The name of this module ("RealWorldValueMappingItemMacro")
-  static const OFString m_ModuleName;
-
-  /// Measurement Units Code Sequence
-  CodeSequenceMacro m_MeasurementUnitsCode;
+    /// Measurement Units Code Sequence
+    CodeSequenceMacro m_MeasurementUnitsCode;
 
-  /// Quantity Definition Sequence
-  OFVector<ContentItemMacro*> m_QuantityDefinitionSequence;
+    /// Quantity Definition Sequence
+    OFVector<ContentItemMacro*> m_QuantityDefinitionSequence;
 };
 
 #endif // FGREALWORLDVALUEMAPPING_H
index 153e8818d68861d8f318ab0ce744b25e5983da9c..1a060df931cfa9b75aebb82ef6063853bf6776e7 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -23,6 +23,7 @@
 #define FGSEG_H
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcitem.h"
 #include "dcmtk/dcmdata/dcsequen.h"
 #include "dcmtk/dcmdata/dcvrus.h"
@@ -34,95 +35,95 @@ class DCMTK_DCMFG_EXPORT FGSegmentation : public FGBase
 {
 
 public:
-
-  /** Constructor, creates empty functional group
-   */
-  FGSegmentation();
-
-  /** Destructor, frees memory
-   */
-  virtual ~FGSegmentation();
-
-  /** Returns a deep copy of this object
-   *  @return Deep copy of this object
-   */
-  virtual FGBase *clone() const;
-
-  /** Returns that this functional group can be used shared or per-frame,
-   *  i.e.\ both
-   *  @return Always returns DcmFGTypes::EFGS_BOTH
-   */
-  virtual DcmFGTypes::E_FGSharedType getSharedType() const {return DcmFGTypes::EFGS_BOTH;}
-
-  /** Clear all data
-   */
-  virtual void clearData();
-
-  /** Check whether data in this functional group is valid
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  OFCondition check() const;
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGSegmentation) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the  first component that does not match
-   *          is lower in the rhs object, or all compared components match
-   *          but the rhs component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in the rhs object, or all compared components match
-   *          but the rhs component is longer.
-   */
-  virtual int compare(const FGBase& rhs) const;
-
-  /** Get Referenced Segment Number
-   *  @param  value  Reference to variable in which the value should be stored
-   *  @param  pos Index value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getReferencedSegmentNumber(Uint16 &value,
-                                                 const unsigned long pos = 0);
-
-  /** Set Referenced Segment Number
-   *  @param  segmentNumber Value to be set
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setReferencedSegmentNumber(const Uint16 &segmentNumber);
-
-  /** Read functional group from item, must contain the Segment Identification
-   *  Sequence
-   *  @param  item The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& item);
-
-  /** Write functional group to item, will write Segment Identification
-   *  Sequence
-   *  @param  item The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
+    /** Constructor, creates empty functional group
+     */
+    FGSegmentation();
+
+    /** Destructor, frees memory
+     */
+    virtual ~FGSegmentation();
+
+    /** Returns a deep copy of this object
+     *  @return Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Returns that this functional group can be used shared or per-frame,
+     *  i.e.\ both
+     *  @return Always returns DcmFGTypes::EFGS_BOTH
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clear all data
+     */
+    virtual void clearData();
+
+    /** Check whether data in this functional group is valid
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    OFCondition check() const;
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGSegmentation) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the  first component that does not match
+     *          is lower in the rhs object, or all compared components match
+     *          but the rhs component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in the rhs object, or all compared components match
+     *          but the rhs component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+    /** Get Referenced Segment Number
+     *  @param  value  Reference to variable in which the value should be stored
+     *  @param  pos Index value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getReferencedSegmentNumber(Uint16& value, const unsigned long pos = 0);
+
+    /** Set Referenced Segment Number
+     *  @param  segmentNumber Value to be set
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setReferencedSegmentNumber(const Uint16& segmentNumber);
+
+    /** Read functional group from item, must contain the Segment Identification
+     *  Sequence
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Write functional group to item, will write Segment Identification
+     *  Sequence
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
 
 private:
-
-  /// Referenced Segment Number: (US, 1-n, 1)
-  /// Represents single value within the single permitted item of the
-  /// Segment Identification Sequence being the data structure the
-  /// Segmentation FG is made of.
-  DcmUnsignedShort m_ReferencedSegmentNumber;
+    /// Referenced Segment Number: (US, 1-n, 1)
+    /// Represents single value within the single permitted item of the
+    /// Segment Identification Sequence being the data structure the
+    /// Segmentation FG is made of.
+    DcmUnsignedShort m_ReferencedSegmentNumber;
 };
 
 #endif // FGSEG_H
diff --git a/dcmfg/include/dcmtk/dcmfg/fgtemporalposition.h b/dcmfg/include/dcmtk/dcmfg/fgtemporalposition.h
new file mode 100644 (file)
index 0000000..73365af
--- /dev/null
@@ -0,0 +1,130 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the Temporal Position Functional Group
+ *
+ */
+
+#ifndef FGTEMPORALPOSITION_H
+#define FGTEMPORALPOSITION_H
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dcitem.h"
+#include "dcmtk/dcmdata/dctk.h" // TODO: include only needed VRs
+#include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/dcmfg/fgdefine.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+
+/** Class representing the Temporal Position Functional Group Macro.
+ */
+class DCMTK_DCMFG_EXPORT FGTemporalPosition : public FGBase
+{
+public:
+    /** Constructor, creates empty Temporal Position Functional Group
+     */
+    FGTemporalPosition();
+
+    /** Destructor, frees memory
+     */
+    virtual ~FGTemporalPosition();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Get shared type of this functional group (can be both, per-frame and
+     *  shared)
+     *  @return Always returns EFGS_BOTH
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    /** Clears all data
+     */
+    virtual void clearData();
+
+    /** Check whether functional group contains valid data
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read functional group from given item, i.e.\ read Temporal Position Sequence
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Write functional group to given item, i.e.\ write Temporal Position Sequence
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Get TemporalPositionTimeOffset
+     *  Time offset of the frame in the set of frames with different temporal positions, in seconds.
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getTemporalPositionTimeOffset(Float64& value, const unsigned long pos = 0) const;
+
+    /** Set TemporalPositionTimeOffset
+     *  Time offset of the frame in the set of frames with different temporal positions, in seconds.
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (FD) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setTemporalPositionTimeOffset(const Float64& value, const OFBool checkValue = OFTrue);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
+
+protected:
+    /* Content of Temporal Position Functional Group Macro */
+
+    /// TemporalPositionTimeOffset (FD, VM 1, Required type 1)
+    /// Time offset of the frame in the set of frames with different temporal positions, in seconds.
+    DcmFloatingPointDouble m_TemporalPositionTimeOffset;
+};
+
+#endif // FGTEMPORALPOSITION_H
index f790cb7a773b1eaf38a6d4a314614e4ce58a9892..0d19a59ec364b8e0529a811a36a8643551f48e62 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define FGTYPES_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/oflog/oflog.h"
+
 #include "dcmtk/dcmdata/dctk.h"
 #include "dcmtk/dcmfg/fgdefine.h"
+#include "dcmtk/oflog/oflog.h"
 
 class FGBase;
 class FunctionalGroups;
@@ -38,19 +39,17 @@ extern DCMTK_DCMFG_EXPORT OFLogger DCM_dcmfgLogger;
 
 #define DCMFG_TRACE(msg) OFLOG_TRACE(DCM_dcmfgLogger, msg)
 #define DCMFG_DEBUG(msg) OFLOG_DEBUG(DCM_dcmfgLogger, msg)
-#define DCMFG_INFO(msg)  OFLOG_INFO(DCM_dcmfgLogger, msg)
-#define DCMFG_WARN(msg)  OFLOG_WARN(DCM_dcmfgLogger, msg)
+#define DCMFG_INFO(msg) OFLOG_INFO(DCM_dcmfgLogger, msg)
+#define DCMFG_WARN(msg) OFLOG_WARN(DCM_dcmfgLogger, msg)
 #define DCMFG_ERROR(msg) OFLOG_ERROR(DCM_dcmfgLogger, msg)
 #define DCMFG_FATAL(msg) OFLOG_FATAL(DCM_dcmfgLogger, msg)
 
-
 // include this file in doxygen documentation
 
 /** @file fgtypes.h
  *  @brief type definitions, constants and helper functions for the dcmfg module
  */
 
-
 /*-----------------------*
  *  constant definitions  *
  *-----------------------*/
@@ -61,33 +60,47 @@ extern DCMTK_DCMFG_EXPORT OFLogger DCM_dcmfgLogger;
  */
 
 /// Functional group already exists
-extern DCMTK_DCMFG_EXPORT   const OFConditionConst     FG_EC_DoubledFG;
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_DoubledFG;
 /// Specified functional group does not exist
-extern DCMTK_DCMFG_EXPORT   const OFConditionConst     FG_EC_NoSuchGroup;
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_NoSuchGroup;
 /// Not enough items
-extern DCMTK_DCMFG_EXPORT   const OFConditionConst     FG_EC_NotEnoughItems;
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_NotEnoughItems;
 /// Too many Items
-extern DCMTK_DCMFG_EXPORT   const OFConditionConst     FG_EC_TooManyItems;
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_TooManyItems;
 /// Invalid data
-extern DCMTK_DCMFG_EXPORT   const OFConditionConst     FG_EC_InvalidData;
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_InvalidData;
 /// Could not write functional group
-extern DCMTK_DCMFG_EXPORT   const OFConditionConst     FG_EC_CouldNotWriteFG;
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_CouldNotWriteFG;
 /// Could not insert functional group
-extern DCMTK_DCMFG_EXPORT   const OFConditionConst     FG_EC_CouldNotInsertFG;
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_CouldNotInsertFG;
 /// No such shared functional group
-extern DCMTK_DCMFG_EXPORT   const OFConditionConst     FG_EC_NoSharedFG;
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_NoSharedFG;
 /// No such per-frame functional group
-extern DCMTK_DCMFG_EXPORT   const OFConditionConst     FG_EC_NoPerFrameFG;
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_NoPerFrameFG;
 /// Could not create functional group
-extern DCMTK_DCMFG_EXPORT   const OFConditionConst     FG_EC_CouldNotCreateFG;
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_CouldNotCreateFG;
 /// Could not create functional group
-extern DCMTK_DCMFG_EXPORT   const OFConditionConst     FG_EC_CouldNotReadSourceImage;
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_CouldNotReadSourceImage;
 /// Could not create functional group
-extern DCMTK_DCMFG_EXPORT   const OFConditionConst     FG_EC_CouldNotAddFG;
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_CouldNotAddFG;
 /// Not enough frames found
-extern DCMTK_DCMFG_EXPORT   const OFConditionConst     FG_EC_NotEnoughFrames;
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_NotEnoughFrames;
 /// No stacks specified (but expected)
-extern DCMTK_DCMFG_EXPORT   const OFConditionConst     FG_EC_NoStacksFound;
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_NoStacksFound;
+/// SOP Class does allow Concatenations
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_SOPClassForbidsConcatenations;
+/// Pixel Data is missing
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_PixelDataMissing;
+/// Pixel Data dimensions invalid
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_PixelDataDimensionsInvalid;
+/// Pixel Data element too large
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_PixelDataTooLarge;
+/// Inconsistent Concatenation Data
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_InconsistentConcatenationData;
+/// Concatenation Complete - no more data available
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_ConcatenationComplete;
+/// Unsupported pixel data layout
+extern DCMTK_DCMFG_EXPORT const OFConditionConst FG_EC_UnsupportedPixelDataLayout;
 
 /*---------------------*
  *  class declaration  *
@@ -100,120 +113,138 @@ class DCMTK_DCMFG_EXPORT DcmFGTypes
 {
 
 public:
-
-  // --- Type definitions ---
-
-  /** Functional group types
-   */
-  enum E_FGType
-  {
-    /// Undefined functional group
-    EFG_UNDEFINED,
-    /// Unknown functional group
-    EFG_UNKNOWN,
-    /// Cardiac Synchronization
-    EFG_CARDIACSYNC,
-    /// Contrast/Bolus Usage
-    EFG_CONTRASTBOLUSUSAGE,
-    /// Derivation Image
-    EFG_DERIVATIONIMAGE,
-    /// Frame Anatomy
-    EFG_FRAMEANATOMY,
-    /// Frame Content
-    EFG_FRAMECONTENT,
-    /// Frame Display Shutter
-    EFG_FRAMEDISPLAYSHUTTER,
-    /// Frame Pixel Shift
-    EFG_FRAMEPIXELSHIFT,
-    /// "Frame VOI LUT" or "Frame VOI LUT with LUT" Macro (share same starting sequence)
-    EFG_FRAMEVOILUTMETA,
-    /// Image Data Type
-    EFG_IMAGEDATATYPE,
-    /// Irradiation Event Identification
-    EFG_IRRADIATIONEVENTIDENT,
-    /// Parametric Map Frame Type
-    EFG_PARAMETRICMAPFRAMETYPE,
-    /// Patient Orientation in Frame
-    EFG_PATIENTORIENTINFRAME,
-    /// Patient Physiological State
-    EFG_PATIENTPHYSIOSTATE,
-    /// Pixel Intensity Relationship LUT
-    EFG_PIXELINTENSITYRELLUT,
-    /// Pixel Measures
-    EFG_PIXELMEASURES,
-    /// "Pixel Value Transformation" or "Identity Pixel Value Transformation"
-    /// (both share the same sequence and attributes)
-    EFG_PIXELVALUETRANSMETA,
-    /// Plane Orientation (Volume)
-    EFG_PLANEORIENTVOLUME,
-    /// Plane Position (Volume)
-    EFG_PLANEPOSITIONVOLUME,
-    /// Plane Position (Patient)
-    EFG_PLANEPOSPATIENT,
-    /// Plane Orientation (Patient)
-    EFG_PLANEORIENTPATIENT,
-    /// Radiopharmaceutical Usage
-    EFG_RADIOPHARAMAUSAGE,
-    /// Real World Value Mapping
-    EFG_REALWORLDVALUEMAPPING,
-    /// Respiratory Synchronization
-    EFG_RESPIRATORYSYNC,
-    /// Segmentation Macro
-    EFG_SEGMENTATION,
-    /// Temporal Position Macro
-    EFG_TEMPORALPOSITION,
-    /// Unassigned Shared Converted Attributes Macro
-    EFG_UNASSIGNEDSHAREDCONVERTEDATTRIBUTES,
-    /// US Image Description Macro
-    EFG_USIMAGEDESCRIPTION
-  };
-
-  /** Functional group types
-   */
-  enum E_FGSharedType
-  {
-    /// Unknown
-    EFGS_UNKNOWN,
-    /// Functional Group can be shared or per-frame
-    EFGS_BOTH,
-    /// Functional Group can only be shared (not per-frame)
-    EFGS_ONLYSHARED,
-    /// Functional Group can only be per-frame (not shared)
-    EFGS_ONLYPERFRAME
-  };
-
-  /** US Image Description Frame Type (first value)
-   */
-  enum E_FGUSFrameType
-  {
-    /// Unknown
-    EFGFT_UNKNOWN,
-    /// ORIGINAL
-    EFGFT_ORIGINAL,
-    /// DERIVED
-    EFGFT_DERIVED
-  };
-
-  // -- static helpers --
-
-  /** Returns functional group type based on tag key
-   *  @param  key The key to get the group type for
-   *  @return The functional group type
-   */
-  static E_FGType tagKey2FGType(const DcmTagKey& key);
-
-  /** Returns the name of the functional group based on the group type
-   *  @param  fgType The functional group type
-   *  @return The name of the functional group
-   */
-  static OFString FGType2OFString(const E_FGType fgType);
-
-  /** Returns the name of a functional group based on a given tag key
-   *  @param  key The tag key to get the functional group type for
-   *  @return The name of the functional group
-   */
-  static OFString tagKey2FGString(const DcmTagKey& key);
-
+    // --- Type definitions ---
+
+    /** Functional group types
+     */
+    enum E_FGType
+    {
+        /// Undefined functional group
+        EFG_UNDEFINED,
+        /// Unknown functional group
+        EFG_UNKNOWN,
+        /// Cardiac Synchronization
+        EFG_CARDIACSYNC,
+        /// Contrast/Bolus Usage
+        EFG_CONTRASTBOLUSUSAGE,
+        /// CT Acquisition Details
+        EFG_CTACQUISITIONDETAILS,
+        /// CT Acquisition Type
+        EFG_CTACQUISITIONTYPE,
+        /// CT Additional X-Ray Source
+        EFG_CTADDITIONALXRAYSOURCE,
+        /// CT Exposure
+        EFG_CTEXPOSURE,
+        /// CT Geometry
+        EFG_CTGEOMETRY,
+        /// CT Image Frame Type
+        EFG_CTIMAGEFRAMETYPE,
+        /// CT Position
+        EFG_CTPOSITION,
+        /// CT Reconstruction
+        EFG_CTRECONSTRUCTION,
+        /// CT Table Dynamics
+        EFG_CTTABLEDYNAMICS,
+        /// CT X-Ray Details
+        EFG_CTXRAYDETAILS,
+        /// Derivation Image
+        EFG_DERIVATIONIMAGE,
+        /// Frame Anatomy
+        EFG_FRAMEANATOMY,
+        /// Frame Content
+        EFG_FRAMECONTENT,
+        /// Frame Display Shutter
+        EFG_FRAMEDISPLAYSHUTTER,
+        /// Frame Pixel Shift
+        EFG_FRAMEPIXELSHIFT,
+        /// "Frame VOI LUT" or "Frame VOI LUT with LUT" Macro (share same starting sequence)
+        EFG_FRAMEVOILUTMETA,
+        /// Image Data Type
+        EFG_IMAGEDATATYPE,
+        /// Irradiation Event Identification
+        EFG_IRRADIATIONEVENTIDENT,
+        /// Parametric Map Frame Type
+        EFG_PARAMETRICMAPFRAMETYPE,
+        /// Patient Orientation in Frame
+        EFG_PATIENTORIENTINFRAME,
+        /// Patient Physiological State
+        EFG_PATIENTPHYSIOSTATE,
+        /// Pixel Intensity Relationship LUT
+        EFG_PIXELINTENSITYRELLUT,
+        /// Pixel Measures
+        EFG_PIXELMEASURES,
+        /// "Pixel Value Transformation", "Identity Pixel Value Transformation", or
+        /// "CT Pixel Value Transformation"; all the same sequence and attributes.
+        EFG_PIXELVALUETRANSMETA,
+        /// Plane Orientation (Volume)
+        EFG_PLANEORIENTVOLUME,
+        /// Plane Position (Volume)
+        EFG_PLANEPOSITIONVOLUME,
+        /// Plane Position (Patient)
+        EFG_PLANEPOSPATIENT,
+        /// Plane Orientation (Patient)
+        EFG_PLANEORIENTPATIENT,
+        /// Radiopharmaceutical Usage
+        EFG_RADIOPHARAMAUSAGE,
+        /// Real World Value Mapping
+        EFG_REALWORLDVALUEMAPPING,
+        /// Respiratory Synchronization
+        EFG_RESPIRATORYSYNC,
+        /// Segmentation Macro
+        EFG_SEGMENTATION,
+        /// Temporal Position Macro
+        EFG_TEMPORALPOSITION,
+        /// Unassigned Shared Converted Attributes Macro
+        EFG_UNASSIGNEDSHAREDCONVERTEDATTRIBUTES,
+        /// US Image Description Macro
+        EFG_USIMAGEDESCRIPTION
+    };
+
+    /** Functional group types
+     */
+    enum E_FGSharedType
+    {
+        /// Unknown
+        EFGS_UNKNOWN,
+        /// Functional Group can be shared or per-frame
+        EFGS_BOTH,
+        /// Functional Group can only be shared (not per-frame)
+        EFGS_ONLYSHARED,
+        /// Functional Group can only be per-frame (not shared)
+        EFGS_ONLYPERFRAME
+    };
+
+    /** US Image Description Frame Type (first value)
+     */
+    enum E_FGUSFrameType
+    {
+        /// Unknown
+        EFGFT_UNKNOWN,
+        /// ORIGINAL
+        EFGFT_ORIGINAL,
+        /// DERIVED
+        EFGFT_DERIVED
+    };
+
+    // -- static helpers --
+
+    /** Returns functional group type based on tag key
+     *  @param  key The key to get the group type for
+     *  @return The functional group type
+     */
+    static E_FGType tagKey2FGType(const DcmTagKey& key);
+
+    /** Returns the name of the functional group based on the group type
+     *  @param  fgType The functional group type
+     *  @return The name of the functional group
+     */
+    static OFString FGType2OFString(const E_FGType fgType);
+
+    /** Returns the name of a functional group based on a given tag key
+     *  @param  key The tag key to get the functional group type for
+     *  @return The name of the functional group
+     */
+    static OFString tagKey2FGString(const DcmTagKey& key);
 };
 
 #endif // FGTYPES_H
index cfc3fcc1f80c1f0dcdf0c5fe916efe037c087d2a..35b0c587375f1e584b2846a61c78aafd41e347a5 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define FGUSIMAGEDESCRIPTION_H
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcitem.h"
-#include "dcmtk/dcmfg/fgtypes.h"
 #include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/dcmfg/fgtypes.h"
 
 /** Class representing the US Image Description Functional Group
  */
-class DCMTK_DCMFG_EXPORT FGUSImageDescription: public FGBase
+class DCMTK_DCMFG_EXPORT FGUSImageDescription : public FGBase
 {
 public:
-
-  /** Constructor, creates empty functional group
-   */
-  FGUSImageDescription();
-
-  /** Destructor, frees memory
-   */
-  virtual ~FGUSImageDescription();
-
-  /** Returns a deep copy of this object
-   *  @return  Deep copy of this object
-   */
-  virtual FGBase *clone() const;
-
-  /** Clears all data
-   */
-  virtual void clearData();
-
-  /** Check whether data in this functional group is valid
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  virtual OFCondition check() const;
-
-  /** Read functional group from item, must contain the US Image Description
-   *  Sequence
-   *  @param  item The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem &item);
-
-  /** Write functional group to item, will write to US Image Description
-   *  Sequence
-   *  @param  item The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
-
-  /** Get shared type of this functional group (can be both, shared and
-   *  per-frame)
-   *  @return Always returns DcmFGTypes::EFGS_BOTH
-   */
-  virtual DcmFGTypes::E_FGSharedType getSharedType() const {return DcmFGTypes::EFGS_BOTH;}
-
-  // --- get() functionality ---
-
-  /** Get Frame Type
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getFrameType(OFString& value,
-                                   const signed long pos = 0);
-
-  /** Get Volumetric Properties
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getVolumetricProperties(OFString& value,
-                                              const signed long pos = 0);
-
-  /** Get Volume Based Calculation Technique
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getVolumeBasedCalculationTechnique(OFString& value,
-                                                         const signed long pos = 0);
-
-  // --- set() functionality ---
-
-  /** Set Frame Type. Frame Type contains up to four values. Value 3 and 4 are
-   *  optional and can be left empty if desired. The values in their order
-   *  of occurrence are:
-   *  1) Pixel Data Characteristics: Either ORIGINAL or DERIVED
-   *  2) Patient Examination Characteristics: Fixed to "PRIMARY", thus cannot be
-   *  influenced through this function.
-   *  3) Image Flavor: Defined Terms listed in the standard
-   *  4) Derived Pixel Contrast: Defined Terms listed in the standard
-   *  @param  pixelDataChar Value 1 of Frame Type
-   *  @param  imageFlavor Value 3 of Frame Type
-   *  @param  derivedPixelContrast Value 4 of Frame Type
-   *  @param  checkValue If OFTrue, the value is checked for conformance.
-   *  @return EC_Normal if setting was successful, error otherwise.
-   */
-  virtual OFCondition setFrameType(const DcmFGTypes::E_FGUSFrameType pixelDataChar,
-                                   const OFString& imageFlavor = "",
-                                   const OFString& derivedPixelContrast = "",
-                                   const OFBool checkValue = OFTrue);
-
-  /** Set Volumetric Properties
-   *  @param  value The value to set. Permitted values:
-   *          "VOLUME", "SAMPLED", "DISTORTED", "MIXED"
-   *  @param  checkValue If OFTrue, the value is checked for conformance
-   *  @return EC_Normal if setting was successful, error otherwise.
-   */
-  virtual OFCondition setVolumetricProperties(const OFString& value,
-                                              const OFBool checkValue = OFTrue);
-
-  /** Set Volume Based Calculation Technique
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setVolumeBasedCalculationTechnique(const OFString& value,
-                                                         const OFBool checkValue = OFTrue);
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  functional groups (this and rhs parameter) are compared by value!
-   *  Both objects (this and rhs) need to have the same type (i.e.\ both
-   *  FGUnknown) to be comparable. This function is used in order
-   *  to decide whether a functional group already exists, or is new. This
-   *  is used in particular to find out whether a given functional group
-   *  can be shared (i.e.\ the same information already exists as shared
-   *  functional group) or is different from the same shared group. In that
-   *  case the shared functional group must be distributed into per-frame
-   *  functional groups, instead. The exact implementation for implementing
-   *  the comparison is not relevant. However, it must be a comparison
-   *  by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the this object, or all compared components match
-   *          but this component is shorter. Also returned if this type and
-   *          rhs type (DcmFGTypes::E_FGType) do not match.
-   *          1 if either the value of the first component that does not match
-   *          is greater in this object, or all compared components match
-   *          but this component is longer.
-   */
-  virtual int compare(const FGBase& rhs) const;
+    /** Constructor, creates empty functional group
+     */
+    FGUSImageDescription();
+
+    /** Destructor, frees memory
+     */
+    virtual ~FGUSImageDescription();
+
+    /** Returns a deep copy of this object
+     *  @return  Deep copy of this object
+     */
+    virtual FGBase* clone() const;
+
+    /** Clears all data
+     */
+    virtual void clearData();
+
+    /** Check whether data in this functional group is valid
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual OFCondition check() const;
+
+    /** Read functional group from item, must contain the US Image Description
+     *  Sequence
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
+
+    /** Write functional group to item, will write to US Image Description
+     *  Sequence
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Get shared type of this functional group (can be both, shared and
+     *  per-frame)
+     *  @return Always returns DcmFGTypes::EFGS_BOTH
+     */
+    virtual DcmFGTypes::E_FGSharedType getSharedType() const
+    {
+        return DcmFGTypes::EFGS_BOTH;
+    }
+
+    // --- get() functionality ---
+
+    /** Get Frame Type
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getFrameType(OFString& value, const signed long pos = 0);
+
+    /** Get Volumetric Properties
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getVolumetricProperties(OFString& value, const signed long pos = 0);
+
+    /** Get Volume Based Calculation Technique
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getVolumeBasedCalculationTechnique(OFString& value, const signed long pos = 0);
+
+    // --- set() functionality ---
+
+    /** Set Frame Type. Frame Type contains up to four values. Value 3 and 4 are
+     *  optional and can be left empty if desired. The values in their order
+     *  of occurrence are:
+     *  1) Pixel Data Characteristics: Either ORIGINAL or DERIVED
+     *  2) Patient Examination Characteristics: Fixed to "PRIMARY", thus cannot be
+     *  influenced through this function.
+     *  3) Image Flavor: Defined Terms listed in the standard
+     *  4) Derived Pixel Contrast: Defined Terms listed in the standard
+     *  @param  pixelDataChar Value 1 of Frame Type
+     *  @param  imageFlavor Value 3 of Frame Type
+     *  @param  derivedPixelContrast Value 4 of Frame Type
+     *  @param  checkValue If OFTrue, the value is checked for conformance.
+     *  @return EC_Normal if setting was successful, error otherwise.
+     */
+    virtual OFCondition setFrameType(const DcmFGTypes::E_FGUSFrameType pixelDataChar,
+                                     const OFString& imageFlavor          = "",
+                                     const OFString& derivedPixelContrast = "",
+                                     const OFBool checkValue              = OFTrue);
+
+    /** Set Volumetric Properties
+     *  @param  value The value to set. Permitted values:
+     *          "VOLUME", "SAMPLED", "DISTORTED", "MIXED"
+     *  @param  checkValue If OFTrue, the value is checked for conformance
+     *  @return EC_Normal if setting was successful, error otherwise.
+     */
+    virtual OFCondition setVolumetricProperties(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Volume Based Calculation Technique
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setVolumeBasedCalculationTechnique(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  functional groups (this and rhs parameter) are compared by value!
+     *  Both objects (this and rhs) need to have the same type (i.e.\ both
+     *  FGUnknown) to be comparable. This function is used in order
+     *  to decide whether a functional group already exists, or is new. This
+     *  is used in particular to find out whether a given functional group
+     *  can be shared (i.e.\ the same information already exists as shared
+     *  functional group) or is different from the same shared group. In that
+     *  case the shared functional group must be distributed into per-frame
+     *  functional groups, instead. The exact implementation for implementing
+     *  the comparison is not relevant. However, it must be a comparison
+     *  by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the this object, or all compared components match
+     *          but this component is shorter. Also returned if this type and
+     *          rhs type (DcmFGTypes::E_FGType) do not match.
+     *          1 if either the value of the first component that does not match
+     *          is greater in this object, or all compared components match
+     *          but this component is longer.
+     */
+    virtual int compare(const FGBase& rhs) const;
 
 private:
+    /* Content of US Image Description Macro */
 
-  /* Content of US Image Description Macro */
-
-  /// Frame Type (CS, VM 4, Required type 1)
-  DcmCodeString m_FrameType;
+    /// Frame Type (CS, VM 4, Required type 1)
+    DcmCodeString m_FrameType;
 
-  /// Volumetric Properties (CS 1, VM 1, Required Type 1)
-  DcmCodeString m_VolumetricProperties;
+    /// Volumetric Properties (CS 1, VM 1, Required Type 1)
+    DcmCodeString m_VolumetricProperties;
 
-  /// Volume Based Calculation Technique (CS, VM 1, Required Type 1)
-  DcmCodeString m_VolumeBasedCalculationTechnique;
+    /// Volume Based Calculation Technique (CS, VM 1, Required Type 1)
+    DcmCodeString m_VolumeBasedCalculationTechnique;
 };
 
 #endif // FGUSIMAGEDESCRIPTION_H
-
index a04b84a2191a6077992187cea8600ebf47c8cbe5..28956f7e21fa26e28d2f53f2dbebbbd2b5b45412 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define FGSTACK_H
 
 #include "dcmtk/config/osconfig.h"
-#include <dcmtk/ofstd/ofmap.h>
+
+#include "dcmtk/dcmfg/fgdefine.h"
 #include "dcmtk/ofstd/ofstring.h"
 #include "dcmtk/ofstd/ofvector.h"
-#include "dcmtk/dcmfg/fgdefine.h"
+#include <dcmtk/ofstd/ofmap.h>
 
 /** Class representing a stack in the context of an Enhanced DICOM object.
  *  Therefore the class stores the ID of the stack (Stack ID) and all the frame
 class DCMTK_DCMFG_EXPORT FGStack
 {
 public:
-
-  // Make sure the main interface class has easy access to internal members
-  friend class FGStackInterface;
-
-  /// Iterator type for iterating over the frames of a stack
-  typedef OFMap<Uint32,Uint32>::iterator iterator;
-
-  /// Const iterator for iterating over the frames of a stack
-  typedef OFMap<Uint32,Uint32>::const_iterator const_iterator;
-
-  /** Constructor, creates stack from Stack ID and assigned frame numbers
-   *  @param  stackID The Stack ID of the stack
-   *  @param  frameNumbers A map with frame numbers as the keys, and the
-   *          position of the frame within the stack as the value for each
-   *          frame. First position is 1. There may be frames having the same
-   *          positions in the same stack. However, in that case the standard
-   *          lists some elements which at least must have the same values, then:
-   *          - Dimension Organization UID (0020,9164) to qualify the Stack ID
-   *          - Image Position (Patient) (0020,0032)
-   *          - Image Orientation (Patient) (0020,0037)
-   *          - Rows (0028,0010) * first value of Pixel Spacing (0028,0030) (= field of view in the row direction)
-   *          - Columns (0028,0011) * second value of Pixel Spacing (0028,0030) (= field of view in the column direction)
-   *          - Slice Thickness (0018,0050)
-   *         The values may change over time (last check was DICOM 2014a), so
-   *         the latest edition of the standard should be consulted if it is
-   *         planned to apply the same in-stack position to different frames.
-   */
-  FGStack(const OFString& stackID,
-          const OFMap<Uint32, Uint32> frameNumbers);
-
-  /** Constructor, create empty stack with given Stack ID (and fill in frames
-   *  later)
-   *  @param  stackID The Stack ID of the frame
-   */
-  FGStack(const OFString& stackID);
-
-  /** Virtual destructor, frees memory
-   */
-  virtual ~FGStack();
-
-  /** Return const iterator to first frame (not sorted after stack position)
-   *  @return Const iterator to first frame
-   */
-  const_iterator begin() const;
-
-  /** Return iterator to first frame (not sorted after stack position)
-   *  @return Iterator to first frame
-   */
-  iterator begin();
-
-  /** Return const iterator pointing behind last frame (not sorted after stack position)
-   *  @return Const iterator pointing behind last frame
-   */
-  const_iterator end() const;
-
-  /** Return iterator pointing behind last frame (not sorted after stack position)
-   *  @return Iterator pointing behind last frame
-   */
-  iterator end();
-
-  /** Add frame to stack and set its in-stack position. Any old position
-   *  will be overwritten.
-   *  @param  frameNumber The frame number that should be added to the stack
-   *  @param  inStackPos  The position in the stack (starting from 1). More than
-   *          one frame can have the same position in the stack, however there
-   *          are rules (see documentation of constructor and the DICOM
-   *          standard)
-   */
-  virtual OFBool addFrame(const Uint32 frameNumber,
-                          const Uint32 inStackPos);
-
-  /** Get Stack ID uniquely identifying this stack
-   *  @return The Stack ID
-   */
-  virtual OFString getStackID() const;
-
-  /** Get the stack position for a given frame
-   *  @param  frameNumber The number of the frame
-   *  @return The stack position for that frame
-   */
-  Uint32 getInStackPos(const Uint32 frameNumber) const;
-
-  /** Get list of frames that are set to a specific In-Stack Position
-   *  @param  inStackPos In-Stack Position Number to find frames for
-   *  @param  resultFrameNumbers The frame numbers assigned to that stack
-   *          position
-   */
-  void getFramesAtStackPos(const Uint32 inStackPos,
-                           OFVector<Uint32>& resultFrameNumbers);
+    /// Make sure the main interface class has easy access to internal members
+    friend class FGStackInterface;
+
+    /// Iterator type for iterating over the frames of a stack
+    typedef OFMap<Uint32, Uint32>::iterator iterator;
+
+    /// Const iterator for iterating over the frames of a stack
+    typedef OFMap<Uint32, Uint32>::const_iterator const_iterator;
+
+    /** Constructor, creates stack from Stack ID and assigned frame numbers
+     *  @param  stackID The Stack ID of the stack
+     *  @param  frameNumbers A map with frame numbers as the keys, and the
+     *          position of the frame within the stack as the value for each
+     *          frame. First position is 1. There may be frames having the same
+     *          positions in the same stack. However, in that case the standard
+     *          lists some elements which at least must have the same values, then:
+     *          - Dimension Organization UID (0020,9164) to qualify the Stack ID
+     *          - Image Position (Patient) (0020,0032)
+     *          - Image Orientation (Patient) (0020,0037)
+     *          - Rows (0028,0010) * first value of Pixel Spacing (0028,0030) (= field of view in the row direction)
+     *          - Columns (0028,0011) * second value of Pixel Spacing (0028,0030) (= field of view in the column
+     * direction)
+     *          - Slice Thickness (0018,0050)
+     *         The values may change over time (last check was DICOM 2014a), so
+     *         the latest edition of the standard should be consulted if it is
+     *         planned to apply the same in-stack position to different frames.
+     */
+    FGStack(const OFString& stackID, const OFMap<Uint32, Uint32> frameNumbers);
+
+    /** Constructor, create empty stack with given Stack ID (and fill in frames
+     *  later)
+     *  @param  stackID The Stack ID of the frame
+     */
+    FGStack(const OFString& stackID);
+
+    /** Virtual destructor, frees memory
+     */
+    virtual ~FGStack();
+
+    /** Return const iterator to first frame (not sorted after stack position)
+     *  @return Const iterator to first frame
+     */
+    const_iterator begin() const;
+
+    /** Return iterator to first frame (not sorted after stack position)
+     *  @return Iterator to first frame
+     */
+    iterator begin();
+
+    /** Return const iterator pointing behind last frame (not sorted after stack position)
+     *  @return Const iterator pointing behind last frame
+     */
+    const_iterator end() const;
+
+    /** Return iterator pointing behind last frame (not sorted after stack position)
+     *  @return Iterator pointing behind last frame
+     */
+    iterator end();
+
+    /** Add frame to stack and set its in-stack position. Any old position
+     *  will be overwritten.
+     *  @param  frameNumber The frame number that should be added to the stack
+     *  @param  inStackPos  The position in the stack (starting from 1). More than
+     *          one frame can have the same position in the stack, however there
+     *          are rules (see documentation of constructor and the DICOM
+     *          standard)
+     *  @return OFTrue if adding was successful, OFFalse otherwise. So far, always
+     *          returns OFTrue. This might change in the future.
+     */
+    virtual OFBool addFrame(const Uint32 frameNumber, const Uint32 inStackPos);
+
+    /** Get Stack ID uniquely identifying this stack
+     *  @return The Stack ID
+     */
+    virtual OFString getStackID() const;
+
+    /** Get the stack position for a given frame
+     *  @param  frameNumber The number of the frame
+     *  @return The stack position for that frame
+     */
+    Uint32 getInStackPos(const Uint32 frameNumber) const;
+
+    /** Get list of frames that are set to a specific In-Stack Position
+     *  @param  inStackPos In-Stack Position Number to find frames for
+     *  @param  resultFrameNumbers The frame numbers assigned to that stack
+     *          position
+     */
+    void getFramesAtStackPos(const Uint32 inStackPos, OFVector<Uint32>& resultFrameNumbers);
 
 private:
+    /// The Stack ID of this frame
+    OFString m_StackID;
 
-  /// The Stack ID of this frame
-  OFString m_StackID;
-
-  /// Map with frames, key is the frame number, value is the in-stack position.
-  /// More than one frame can have the same in-stack position
-  OFMap<Uint32, Uint32> m_FrameNumbers;
-
+    /// Map with frames, key is the frame number, value is the in-stack position.
+    /// More than one frame can have the same in-stack position
+    OFMap<Uint32, Uint32> m_FrameNumbers;
 };
 
 #endif // STACKREADER_H
index 9c929c70649f79035c3f6a3e37b30076d4af6ff9..e1329c4bf1d5a366d67c0d576fa6e9981bce5fe2 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define STACKINTERFACE_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofmap.h"
-#include "dcmtk/ofstd/ofstring.h"
+
 #include "dcmtk/dcmdata/dctk.h"
 #include "dcmtk/dcmfg/fginterface.h"
 #include "dcmtk/dcmfg/stack.h"
+#include "dcmtk/ofstd/ofmap.h"
+#include "dcmtk/ofstd/ofstring.h"
 
 // Forward declaration
 class FGFrameContent;
 
-
 /** Class for convenient access of stacks within an Enhanced DICOM object
  */
 class DCMTK_DCMFG_EXPORT FGStackInterface
 {
 public:
+    FGStackInterface();
 
-  FGStackInterface();
-
-  OFBool checkConsistency(FGInterface* fgContext = NULL);
+    OFBool checkConsistency(FGInterface* fgContext = NULL);
 
-  virtual void clear();
+    virtual void clear();
 
-  virtual ~FGStackInterface();
+    virtual ~FGStackInterface();
 
-  virtual OFBool addStack(FGStack* stack);
+    virtual OFBool addStack(FGStack* stack);
 
-  virtual OFCondition read(FGInterface& fgSource);
+    virtual OFCondition read(FGInterface& fgSource);
 
-  virtual OFCondition write(FGInterface& fgDestination);
+    virtual OFCondition write(FGInterface& fgDestination);
 
-  size_t numStacks() const;
+    size_t numStacks() const;
 
 protected:
+    FGFrameContent* ensureFrameContentFG(const Uint32 frameNo, FGInterface& fg);
 
-  FGFrameContent* ensureFrameContentFG(const Uint32 frameNo,
-                                       FGInterface& fg);
-
-  // Returns number of errors
-  virtual size_t checkContext(FGStack* stack,
-                              FGInterface* context);
+    // Returns number of errors
+    virtual size_t checkContext(FGStack* stack, FGInterface* context);
 
 private:
-
-  /// The stacks found
-  OFMap<OFString, FGStack*> m_Stacks;
+    /// The stacks found
+    OFMap<OFString, FGStack*> m_Stacks;
 };
 
 #endif // STACKINTERFACE_H
index 6426874d0113889e9d816c7485d71f8b45436a1e..44f3c374708010a0bc8a8ec049005906672d5e6a 100644 (file)
@@ -1,7 +1,19 @@
 # create library from source files
 DCMTK_ADD_LIBRARY(dcmfg
+  concatenationcreator
+  concatenationloader
   fg
   fgbase
+  fgctacquisitiondetails
+  fgctacquisitiontype
+  fgctadditionalxraysource
+  fgctexposure
+  fgctgeometry
+  fgctimageframetype
+  fgctposition
+  fgctreconstruction
+  fgcttabledynamics
+  fgctxraydetails
   fgderimg
   fgfact
   fgfracon
@@ -10,6 +22,7 @@ DCMTK_ADD_LIBRARY(dcmfg
   fgpixeltransform
   fgimagedatatype
   fginterface
+  fgirradiationeventid
   fgpixmsr
   fgparametricmapframetype
   fgplanor
@@ -18,6 +31,7 @@ DCMTK_ADD_LIBRARY(dcmfg
   fgplanposvol
   fgrealworldvaluemapping
   fgseg
+  fgtemporalposition
   fgusimagedescription
   fgtypes
   stack
index 78a385a7fbc0e9a1a9c9117c13ede31298703e25..0e6319b39ca6252ec1b1c6cdf591c4210ecbe76c 100644 (file)
@@ -1,16 +1,26 @@
-fg.o: fg.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmfg/fg.h ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+concatenationcreator.o: concatenationcreator.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../include/dcmtk/dcmfg/fgtypes.h ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
@@ -18,11 +28,12 @@ fg.o: fg.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
  ../../ofstd/include/dcmtk/ofstd/ofvector.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -33,41 +44,35 @@ fg.o: fg.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../include/dcmtk/dcmfg/concatenationcreator.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -95,9 +100,6 @@ fg.o: fg.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
@@ -112,24 +114,28 @@ fg.o: fg.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fgbase.h
-fgbase.o: fgbase.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmfg/fgbase.h ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fgtypes.h
+concatenationloader.o: concatenationloader.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -155,7 +161,6 @@ fgbase.o: fgbase.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
@@ -163,27 +168,44 @@ fgbase.o: fgbase.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../include/dcmtk/dcmfg/concatenationloader.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftuple.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdiag.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/push.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/mmtag.def \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefrd.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuple.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/pop.def ../include/dcmtk/dcmfg/fg.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -194,11 +216,9 @@ fgbase.o: fgbase.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
@@ -211,9 +231,6 @@ fgbase.o: fgbase.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
@@ -227,28 +244,10 @@ fgbase.o: fgbase.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
- ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmfg/fgdefine.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodcommn.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../../dcmiod/include/dcmtk/dcmiod/modpatient.h \
- ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
- ../../dcmiod/include/dcmtk/dcmiod/modpatientstudy.h \
- ../../ofstd/include/dcmtk/ofstd/ofoption.h \
- ../../ofstd/include/dcmtk/ofstd/ofalign.h \
- ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
- ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
- ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
- ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
- ../../dcmiod/include/dcmtk/dcmiod/modsopcommon.h \
- ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h
-fgderimg.o: fgderimg.cc ../../config/include/dcmtk/config/osconfig.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h
+fg.o: fg.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmfg/fg.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
@@ -264,6 +263,13 @@ fgderimg.o: fgderimg.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -289,22 +295,15 @@ fgderimg.o: fgderimg.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../include/dcmtk/dcmfg/fgbase.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../include/dcmtk/dcmfg/fgderimg.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../include/dcmtk/dcmfg/fgtypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
@@ -314,9 +313,8 @@ fgderimg.o: fgderimg.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
  ../../ofstd/include/dcmtk/ofstd/ofmap.h \
@@ -364,32 +362,28 @@ fgderimg.o: fgderimg.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
- ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
- ../include/dcmtk/dcmfg/fgdefine.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodutil.h
-fgfact.o: fgfact.cc ../../config/include/dcmtk/config/osconfig.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../include/dcmtk/dcmfg/fgdefine.h
+fgbase.o: fgbase.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../include/dcmtk/dcmfg/fgbase.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -415,30 +409,17 @@ fgfact.o: fgfact.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmfg/fgfact.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgtypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
@@ -447,10 +428,13 @@ fgfact.o: fgfact.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -461,9 +445,11 @@ fgfact.o: fgfact.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
@@ -493,22 +479,26 @@ fgfact.o: fgfact.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fgderimg.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodcommn.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
  ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
- ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgfracon.h \
- ../include/dcmtk/dcmfg/fgframeanatomy.h \
- ../include/dcmtk/dcmfg/fgframevoilut.h \
- ../include/dcmtk/dcmfg/fgpixeltransform.h \
- ../include/dcmtk/dcmfg/fgimagedatatype.h \
- ../include/dcmtk/dcmfg/fgparametricmapframetype.h \
- ../include/dcmtk/dcmfg/fgpixmsr.h ../include/dcmtk/dcmfg/fgplanor.h \
- ../include/dcmtk/dcmfg/fgplanorvol.h ../include/dcmtk/dcmfg/fgplanpo.h \
- ../include/dcmtk/dcmfg/fgplanposvol.h ../include/dcmtk/dcmfg/fgseg.h \
- ../include/dcmtk/dcmfg/fgusimagedescription.h \
- ../include/dcmtk/dcmfg/fgrealworldvaluemapping.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodcontentitemmacro.h
-fgfracon.o: fgfracon.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modpatient.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modpatientstudy.h \
+ ../../ofstd/include/dcmtk/ofstd/ofoption.h \
+ ../../ofstd/include/dcmtk/ofstd/ofalign.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modsopcommon.h
+fgctacquisitiondetails.o: fgctacquisitiondetails.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
@@ -519,15 +509,8 @@ fgfracon.o: fgfracon.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../include/dcmtk/dcmfg/fgctacquisitiondetails.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -542,6 +525,7 @@ fgfracon.o: fgfracon.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
  ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
@@ -553,40 +537,38 @@ fgfracon.o: fgfracon.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmfg/fgfracon.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -597,9 +579,11 @@ fgfracon.o: fgfracon.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
@@ -630,26 +614,26 @@ fgfracon.o: fgfracon.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
  ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
- ../include/dcmtk/dcmfg/fgdefine.h
-fgframeanatomy.o: fgframeanatomy.cc \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
+fgctacquisitiontype.o: fgctacquisitiontype.cc \
  ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmfg/fgframeanatomy.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmfg/fgctacquisitiontype.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -664,6 +648,7 @@ fgframeanatomy.o: fgframeanatomy.cc \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
  ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
@@ -675,29 +660,32 @@ fgframeanatomy.o: fgframeanatomy.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
@@ -748,16 +736,14 @@ fgframeanatomy.o: fgframeanatomy.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
  ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
  ../include/dcmtk/dcmfg/fgdefine.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
-fgframevoilut.o: fgframevoilut.cc \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
+fgctadditionalxraysource.o: fgctadditionalxraysource.cc \
  ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
@@ -769,15 +755,16 @@ fgframevoilut.o: fgframevoilut.cc \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../include/dcmtk/dcmfg/fgctadditionalxraysource.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -803,30 +790,16 @@ fgframevoilut.o: fgframevoilut.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmfg/fgframevoilut.h ../include/dcmtk/dcmfg/fgbase.h \
- ../include/dcmtk/dcmfg/fgtypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
@@ -835,9 +808,13 @@ fgframevoilut.o: fgframevoilut.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -848,9 +825,11 @@ fgframevoilut.o: fgframevoilut.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
@@ -880,8 +859,14 @@ fgframevoilut.o: fgframevoilut.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmfg/fgdefine.h
-fgimagedatatype.o: fgimagedatatype.cc \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
+fgctexposure.o: fgctexposure.cc \
  ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
@@ -893,15 +878,8 @@ fgimagedatatype.o: fgimagedatatype.cc \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../include/dcmtk/dcmfg/fgctexposure.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -916,6 +894,7 @@ fgimagedatatype.o: fgimagedatatype.cc \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
  ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
@@ -927,41 +906,38 @@ fgimagedatatype.o: fgimagedatatype.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmfg/fgimagedatatype.h ../include/dcmtk/dcmfg/fgbase.h \
- ../include/dcmtk/dcmfg/fgtypes.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -972,9 +948,11 @@ fgimagedatatype.o: fgimagedatatype.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
@@ -1004,31 +982,29 @@ fgimagedatatype.o: fgimagedatatype.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmfg/fgdefine.h
-fginterface.o: fginterface.cc \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
+fgctgeometry.o: fgctgeometry.cc \
  ../../config/include/dcmtk/config/osconfig.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../include/dcmtk/dcmfg/fgctgeometry.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -1041,6 +1017,10 @@ fginterface.o: fginterface.cc \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -1051,40 +1031,1668 @@ fginterface.o: fginterface.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
+fgctimageframetype.o: fgctimageframetype.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmfg/fgctimageframetype.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
+fgctposition.o: fgctposition.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmfg/fgctposition.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
+fgctreconstruction.o: fgctreconstruction.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmfg/fgctreconstruction.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
+fgcttabledynamics.o: fgcttabledynamics.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmfg/fgcttabledynamics.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
+fgctxraydetails.o: fgctxraydetails.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmfg/fgctxraydetails.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
+fgderimg.o: fgderimg.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../include/dcmtk/dcmfg/fgderimg.h ../include/dcmtk/dcmfg/fgbase.h \
+ ../include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h
+fgfact.o: fgfact.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmfg/fgctacquisitiondetails.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../include/dcmtk/dcmfg/fgctacquisitiontype.h \
+ ../include/dcmtk/dcmfg/fgctadditionalxraysource.h \
+ ../include/dcmtk/dcmfg/fgctexposure.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../include/dcmtk/dcmfg/fgctgeometry.h \
+ ../include/dcmtk/dcmfg/fgctimageframetype.h \
+ ../include/dcmtk/dcmfg/fgctposition.h \
+ ../include/dcmtk/dcmfg/fgctreconstruction.h \
+ ../include/dcmtk/dcmfg/fgcttabledynamics.h \
+ ../include/dcmtk/dcmfg/fgctxraydetails.h \
+ ../include/dcmtk/dcmfg/fgderimg.h ../include/dcmtk/dcmfg/fgfact.h \
+ ../include/dcmtk/dcmfg/fgfracon.h \
+ ../include/dcmtk/dcmfg/fgframeanatomy.h \
+ ../include/dcmtk/dcmfg/fgframevoilut.h \
+ ../include/dcmtk/dcmfg/fgimagedatatype.h \
+ ../include/dcmtk/dcmfg/fgirradiationeventid.h \
+ ../include/dcmtk/dcmfg/fgparametricmapframetype.h \
+ ../include/dcmtk/dcmfg/fgpixeltransform.h \
+ ../include/dcmtk/dcmfg/fgpixmsr.h ../include/dcmtk/dcmfg/fgplanor.h \
+ ../include/dcmtk/dcmfg/fgplanorvol.h ../include/dcmtk/dcmfg/fgplanpo.h \
+ ../include/dcmtk/dcmfg/fgplanposvol.h \
+ ../include/dcmtk/dcmfg/fgrealworldvaluemapping.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodcontentitemmacro.h \
+ ../include/dcmtk/dcmfg/fgseg.h \
+ ../include/dcmtk/dcmfg/fgtemporalposition.h \
+ ../include/dcmtk/dcmfg/fgusimagedescription.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
+fgfracon.o: fgfracon.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmfg/fgfracon.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
+fgframeanatomy.o: fgframeanatomy.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmfg/fgframeanatomy.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
+fgframevoilut.o: fgframevoilut.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmfg/fgframevoilut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
+fgimagedatatype.o: fgimagedatatype.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmfg/fgimagedatatype.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
+fginterface.o: fginterface.cc \
+ ../../config/include/dcmtk/config/osconfig.h ../include/dcmtk/dcmfg/fg.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../include/dcmtk/dcmfg/fgbase.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fgfact.h \
  ../include/dcmtk/dcmfg/fginterface.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
+fgirradiationeventid.o: fgirradiationeventid.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmfg/fgirradiationeventid.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -1095,9 +2703,11 @@ fginterface.o: fginterface.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
@@ -1127,9 +2737,13 @@ fginterface.o: fginterface.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmfg/fgtypes.h ../include/dcmtk/dcmfg/fgdefine.h \
- ../include/dcmtk/dcmfg/fg.h ../include/dcmtk/dcmfg/fgbase.h \
- ../include/dcmtk/dcmfg/fgfact.h
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
 fgparametricmapframetype.o: fgparametricmapframetype.cc \
  ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
@@ -1142,15 +2756,16 @@ fgparametricmapframetype.o: fgparametricmapframetype.cc \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../include/dcmtk/dcmfg/fgparametricmapframetype.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -1176,29 +2791,19 @@ fgparametricmapframetype.o: fgparametricmapframetype.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmfg/fgparametricmapframetype.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
@@ -1209,21 +2814,24 @@ fgparametricmapframetype.o: fgparametricmapframetype.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
@@ -1253,7 +2861,12 @@ fgparametricmapframetype.o: fgparametricmapframetype.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmfg/fgdefine.h
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
 fgpixeltransform.o: fgpixeltransform.cc \
  ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
@@ -1266,15 +2879,17 @@ fgpixeltransform.o: fgpixeltransform.cc \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../include/dcmtk/dcmfg/fgpixeltransform.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -1300,60 +2915,52 @@ fgpixeltransform.o: fgpixeltransform.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmfg/fgpixeltransform.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
  ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
@@ -1377,18 +2984,26 @@ fgpixeltransform.o: fgpixeltransform.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmfg/fgdefine.h
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
 fgpixmsr.o: fgpixmsr.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmfg/fgpixmsr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmfg/fgpixmsr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oftraits.h \
@@ -1421,31 +3036,147 @@ fgpixmsr.o: fgpixmsr.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
+fgplanor.o: fgplanor.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmfg/fgfact.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
@@ -1457,11 +3188,13 @@ fgpixmsr.o: fgpixmsr.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
  ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
  ../../ofstd/include/dcmtk/ofstd/oftime.h \
@@ -1494,31 +3227,33 @@ fgpixmsr.o: fgpixmsr.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmfg/fgdefine.h \
+ ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fgplanor.h \
+ ../include/dcmtk/dcmfg/fgbase.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h
-fgplanor.o: fgplanor.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmfg/fgplanor.h ../include/dcmtk/dcmfg/fgbase.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
+fgplanorvol.o: fgplanorvol.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -1533,6 +3268,7 @@ fgplanor.o: fgplanor.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
  ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
@@ -1544,19 +3280,20 @@ fgplanor.o: fgplanor.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../include/dcmtk/dcmfg/fgplanorvol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
@@ -1565,8 +3302,6 @@ fgplanor.o: fgplanor.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
@@ -1611,37 +3346,30 @@ fgplanor.o: fgplanor.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fgfact.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h
-fgplanorvol.o: fgplanorvol.cc \
- ../../config/include/dcmtk/config/osconfig.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
+fgplanpo.o: fgplanpo.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../include/dcmtk/dcmfg/fgfact.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -1668,44 +3396,38 @@ fgplanorvol.o: fgplanorvol.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmfg/fgplanorvol.h ../include/dcmtk/dcmfg/fgbase.h \
- ../include/dcmtk/dcmfg/fgtypes.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -1716,9 +3438,11 @@ fgplanorvol.o: fgplanorvol.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
@@ -1742,30 +3466,41 @@ fgplanorvol.o: fgplanorvol.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmfg/fgdefine.h
-fgplanpo.o: fgplanpo.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmfg/fgplanpo.h ../include/dcmtk/dcmfg/fgbase.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fgplanpo.h \
+ ../include/dcmtk/dcmfg/fgbase.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
+fgplanposvol.o: fgplanposvol.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmfg/fgplanposvol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -1791,7 +3526,6 @@ fgplanpo.o: fgplanpo.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
@@ -1799,11 +3533,10 @@ fgplanpo.o: fgplanpo.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
@@ -1812,7 +3545,6 @@ fgplanpo.o: fgplanpo.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
@@ -1864,14 +3596,13 @@ fgplanpo.o: fgplanpo.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fgfact.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h
-fgplanposvol.o: fgplanposvol.cc \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
+fgrealworldvaluemapping.o: fgrealworldvaluemapping.cc \
  ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
@@ -1883,15 +3614,16 @@ fgplanposvol.o: fgplanposvol.cc \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../include/dcmtk/dcmfg/fgrealworldvaluemapping.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -1917,30 +3649,17 @@ fgplanposvol.o: fgplanposvol.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmfg/fgplanposvol.h ../include/dcmtk/dcmfg/fgbase.h \
- ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
@@ -1949,9 +3668,13 @@ fgplanposvol.o: fgplanposvol.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -1962,9 +3685,11 @@ fgplanposvol.o: fgplanposvol.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
@@ -1994,26 +3719,36 @@ fgplanposvol.o: fgplanposvol.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmfg/fgdefine.h
-fgrealworldvaluemapping.o: fgrealworldvaluemapping.cc \
- ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmfg/fgrealworldvaluemapping.h \
- ../include/dcmtk/dcmfg/fgbase.h ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodcontentitemmacro.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
+fgseg.o: fgseg.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmfg/fgseg.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -2039,7 +3774,6 @@ fgrealworldvaluemapping.o: fgrealworldvaluemapping.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
@@ -2047,11 +3781,13 @@ fgrealworldvaluemapping.o: fgrealworldvaluemapping.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
@@ -2060,11 +3796,8 @@ fgrealworldvaluemapping.o: fgrealworldvaluemapping.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
  ../../ofstd/include/dcmtk/ofstd/ofmap.h \
@@ -2101,7 +3834,6 @@ fgrealworldvaluemapping.o: fgrealworldvaluemapping.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
@@ -2113,26 +3845,26 @@ fgrealworldvaluemapping.o: fgrealworldvaluemapping.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
  ../include/dcmtk/dcmfg/fgdefine.h \
- ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodcontentitemmacro.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
-fgseg.o: fgseg.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmfg/fgseg.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
+fgtemporalposition.o: fgtemporalposition.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmfg/fgtemporalposition.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oftraits.h \
@@ -2165,7 +3897,6 @@ fgseg.o: fgseg.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
@@ -2173,14 +3904,9 @@ fgseg.o: fgseg.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
- ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
@@ -2189,9 +3915,10 @@ fgseg.o: fgseg.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
  ../../ofstd/include/dcmtk/ofstd/ofmap.h \
@@ -2228,6 +3955,7 @@ fgseg.o: fgseg.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
@@ -2238,35 +3966,47 @@ fgseg.o: fgseg.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
  ../include/dcmtk/dcmfg/fgdefine.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h
 fgtypes.o: fgtypes.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmfg/fgtypes.h ../../oflog/include/dcmtk/oflog/oflog.h \
- ../../oflog/include/dcmtk/oflog/logger.h \
- ../../oflog/include/dcmtk/oflog/config.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmfg/fgbase.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
  ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
  ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
@@ -2278,37 +4018,27 @@ fgtypes.o: fgtypes.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
@@ -2359,25 +4089,24 @@ fgtypes.o: fgtypes.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fgbase.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodcommn.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../../dcmiod/include/dcmtk/dcmiod/modpatient.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
  ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modpatient.h \
  ../../dcmiod/include/dcmtk/dcmiod/modpatientstudy.h \
  ../../ofstd/include/dcmtk/ofstd/ofoption.h \
  ../../ofstd/include/dcmtk/ofstd/ofalign.h \
- ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
- ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
- ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
- ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
- ../../dcmiod/include/dcmtk/dcmiod/modsopcommon.h \
- ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h
+ ../../dcmiod/include/dcmtk/dcmiod/modsopcommon.h
 fgusimagedescription.o: fgusimagedescription.cc \
  ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
@@ -2390,15 +4119,16 @@ fgusimagedescription.o: fgusimagedescription.cc \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../include/dcmtk/dcmfg/fgusimagedescription.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -2424,30 +4154,17 @@ fgusimagedescription.o: fgusimagedescription.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmfg/fgusimagedescription.h \
- ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
@@ -2456,9 +4173,13 @@ fgusimagedescription.o: fgusimagedescription.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -2469,9 +4190,11 @@ fgusimagedescription.o: fgusimagedescription.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
@@ -2501,55 +4224,53 @@ fgusimagedescription.o: fgusimagedescription.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fgbase.h
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h
 stack.o: stack.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmfg/stack.h ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../include/dcmtk/dcmfg/stack.h ../include/dcmtk/dcmfg/fgdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../include/dcmtk/dcmfg/fgdefine.h
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h
 stackinterface.o: stackinterface.cc \
+ ../include/dcmtk/dcmfg/stackinterface.h \
  ../../config/include/dcmtk/config/osconfig.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
- ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
- ../../ofstd/include/dcmtk/ofstd/ofcast.h \
- ../../ofstd/include/dcmtk/ofstd/ofexport.h \
- ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
  ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
  ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
@@ -2561,42 +4282,41 @@ stackinterface.o: stackinterface.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmfg/stackinterface.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -2607,9 +4327,11 @@ stackinterface.o: stackinterface.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
@@ -2639,7 +4361,12 @@ stackinterface.o: stackinterface.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmfg/fginterface.h ../include/dcmtk/dcmfg/fgtypes.h \
- ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fg.h \
- ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/stack.h \
- ../include/dcmtk/dcmfg/fgfracon.h
+ ../include/dcmtk/dcmfg/fginterface.h ../include/dcmtk/dcmfg/fg.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../include/dcmtk/dcmfg/stack.h ../include/dcmtk/dcmfg/fgfracon.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
index def09187e822d25cada9e4bd66968f799322d00b..0cacad30855a2869ca2f8d7e457f7b8530cd480c 100644 (file)
@@ -22,12 +22,42 @@ LOCALINCLUDES = -I$(ofstddir)/include -I$(oflogdir)/include \
 
 LOCALDEFS =
 
-objs = fgderimg.o fgframevoilut.o fgpixmsr.o fgplanpo.o fgseg.o stackinterface.o \
-       fgbase.o fgfact.o fgimagedatatype.o fgplanor.o fgplanposvol.o fgtypes.o \
-       fg.o fgfracon.o fginterface.o fgplanorvol.o fgrealworldvaluemapping.o \
-       fgusimagedescription.o fgparametricmapframetype.o \
-       fgpixeltransform.o fgframeanatomy.o stack.o
-
+objs = concatenationcreator.o \
+       concatenationloader.o \
+       fg.o \
+       fgbase.o \
+       fgctacquisitiondetails.o \
+       fgctacquisitiontype.o \
+       fgctadditionalxraysource.o \
+       fgctexposure.o \
+       fgctgeometry.o \
+       fgctimageframetype.o \
+       fgctposition.o \
+       fgctreconstruction.o \
+       fgcttabledynamics.o \
+       fgctxraydetails.o \
+       fgderimg.o \
+       fgfact.o \
+       fgfracon.o \
+       fgframeanatomy.o \
+       fgframevoilut.o \
+       fgpixeltransform.o \
+       fgimagedatatype.o \
+       fginterface.o \
+       fgirradiationeventid.o \
+       fgpixmsr.o \
+       fgparametricmapframetype.o \
+       fgplanor.o \
+       fgplanorvol.o \
+       fgplanpo.o \
+       fgplanposvol.o \
+       fgrealworldvaluemapping.o \
+       fgseg.o \
+       fgtemporalposition.o \
+       fgusimagedescription.o \
+       fgtypes.o \
+       stack.o \
+       stackinterface.o
 
 library = libdcmfg.$(LIBEXT)
 
diff --git a/dcmfg/libsrc/concatenationcreator.cc b/dcmfg/libsrc/concatenationcreator.cc
new file mode 100644 (file)
index 0000000..ff58147
--- /dev/null
@@ -0,0 +1,476 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for creating Concatenations
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmdata/dcitem.h"
+#include "dcmtk/dcmdata/dcpixel.h"
+#include "dcmtk/dcmdata/dcuid.h"
+#include "dcmtk/dcmfg/concatenationcreator.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/ofstd/ofstd.h"
+
+// Maximum number of instances that make up a Concatenation
+const Uint16 ConcatenationCreator::m_MAX_INSTANCES_PER_CONCATENATION = 65535;
+
+/// Maximum number of bytes for uncompressed pixel data (=2^32-2), derived from
+/// 32 bit length field of Pixel Data attribute with even length being required.
+Uint32 const ConcatenationCreator::m_MAX_PIXEL_DATA_LENGTH = 4294967294UL;
+
+
+//  --------------------------------- Public API ------------------------------
+
+// Constructor
+ConcatenationCreator::ConcatenationCreator()
+    : m_configured(OFFalse)
+    , m_cfgTransferOwnership(OFFalse)
+    , m_cfgNumFramesPerInstance(25)
+    , m_numBytesFrame(0)
+    , m_srcDataset(OFnullptr)
+    , m_srcSOPInstanceUID()
+    , m_srcPixelData(OFnullptr)
+    , m_VRPixelData(EVR_UN)
+    , m_srcPerFrameFG(OFnullptr)
+    , m_srcNumFrames(0)
+    , m_dstNumInstances(0)
+    , m_dstNumFramesPerInstance(0)
+    , m_dstNumFramesLastInstance(0)
+    , m_dstConcatenationUID()
+    , m_dstInstanceNumber("1")
+    , m_currentSrcFrame(0)
+    , m_currentPerFrameItem(OFnullptr)
+    , m_currentInstanceNum(0)
+{
+}
+
+ConcatenationCreator::~ConcatenationCreator()
+{
+    if (m_cfgTransferOwnership)
+    {
+        delete m_srcDataset;
+        delete[] m_srcPixelData;
+    }
+}
+
+OFCondition ConcatenationCreator::setCfgInput(DcmItem* srcDataset, OFBool transferOwnership)
+{
+    // Check pixel data exists and is in native format (i.e. uncompressed)
+    DcmElement* elem = NULL;
+    srcDataset->findAndGetElement(DCM_PixelData, elem);
+    if (!elem)
+        return FG_EC_PixelDataMissing;
+    DcmPixelData* pixDataElem = OFstatic_cast(DcmPixelData*, elem);
+    if (!pixDataElem)
+        return FG_EC_PixelDataMissing;
+    if (!pixDataElem->canWriteXfer(EXS_LittleEndianExplicit, EXS_LittleEndianExplicit /* ignored */))
+        return EC_UnsupportedEncoding;
+    OFCondition result = pixDataElem->getUint8Array(m_srcPixelData);
+    if (!m_srcPixelData || result.bad())
+        return FG_EC_PixelDataMissing;
+
+    m_srcDataset = srcDataset;
+
+    m_cfgTransferOwnership = transferOwnership;
+
+    // All fine
+    return EC_Normal;
+}
+
+OFCondition ConcatenationCreator::setCfgInput(DcmItem* srcDataset,
+                                              Uint8* pixelData,
+                                              size_t pixelDataLength,
+                                              OFBool transferOwnership)
+{
+    // Check input parameters
+    if (!pixelData)
+        return FG_EC_PixelDataMissing;
+
+    m_srcDataset           = srcDataset;
+    m_srcPixelData         = pixelData;
+    m_cfgTransferOwnership = transferOwnership;
+
+    // All fine
+    return EC_Normal;
+}
+
+OFCondition ConcatenationCreator::setCfgFramesPerInstance(Uint32 numFramesPerInstance)
+{
+    m_cfgNumFramesPerInstance = numFramesPerInstance;
+    return EC_Normal;
+}
+
+OFBool ConcatenationCreator::setCfgInstanceNumber(const OFString& instanceNumber)
+{
+    if (DcmIntegerString::checkStringValue(instanceNumber, "1").bad())
+        return OFFalse;
+
+    m_dstInstanceNumber = instanceNumber;
+    return OFTrue;
+}
+
+OFCondition ConcatenationCreator::writeNextInstance(DcmItem& dstDataset)
+{
+    OFCondition result;
+    if (!m_configured)
+    {
+        result = configureCommon();
+        if (result.bad())
+        {
+            return result;
+        }
+    }
+
+    // Store number of frames for this instance for later use
+    Uint32 numFramesThisInstance = numFramesCurrentDstInstance();
+    if (numFramesThisInstance == 0)
+    {
+        return FG_EC_ConcatenationComplete;
+    }
+
+    // Clone destination dataset from source dataset,
+    // Remove pixel data and per-frame functional groups before cloning, and re-insert
+    // it again in order to leave the original dataset in unmodified state
+    DcmElement* backup1 = m_srcDataset->remove(DCM_PerFrameFunctionalGroupsSequence);
+    DcmElement* backup2 = m_srcDataset->remove(DCM_PixelData);
+    dstDataset          = *m_srcDataset;
+    m_srcDataset->insert(backup1);
+    m_srcDataset->insert(backup2);
+
+    // Allocate element/buffer for destination pixel data and other heap memory
+    OFunique_ptr<DcmPixelData> dstPixelData(new DcmPixelData(DCM_PixelData));
+    OFunique_ptr<DcmSequenceOfItems> dstPerFrameSeq(new DcmSequenceOfItems(DCM_PerFrameFunctionalGroupsSequence));
+    if (!dstPixelData || !dstPerFrameSeq)
+    {
+        return EC_MemoryExhausted;
+    }
+
+    Uint8* dstData = NULL;
+    size_t numTotalBytesInstance = m_numBytesFrame * numFramesThisInstance;
+    // Cast is safe, checked in configureCommon()
+    dstPixelData->createUint8Array(OFstatic_cast(Uint32, numTotalBytesInstance), dstData);
+    if (!dstData)
+    {
+        return EC_MemoryExhausted;
+    }
+    dstPixelData->setVR(m_VRPixelData);
+    memcpy(dstData, &(m_srcPixelData[m_numBytesFrame * m_currentSrcFrame]), numTotalBytesInstance);
+    result = dstDataset.insert(dstPixelData.release());
+    if (result.good())
+    {
+        // Copy per-frame functional groups for the related frames
+        for (size_t frameCount = 0; frameCount < numFramesThisInstance; frameCount++)
+        {
+            if ((m_currentPerFrameItem == NULL) && (m_currentSrcFrame == m_dstNumInstances - 1))
+            {
+                // Last instance might have less frames
+                break;
+            }
+            else if ((m_currentPerFrameItem == NULL) && (m_currentSrcFrame != m_dstNumInstances - 1))
+            {
+                DCMFG_ERROR("Not enough items in Per-frame Functional group while copying instance #"
+                            << m_currentSrcFrame + 1 << "/" << m_dstNumInstances);
+                result = FG_EC_NotEnoughFrames;
+                break;
+            }
+            DcmItem* newPerFrameItem = OFstatic_cast(DcmItem*, m_currentPerFrameItem->clone());
+            if (newPerFrameItem)
+            {
+                dstPerFrameSeq->insert(newPerFrameItem);
+            }
+            else
+            {
+                result = EC_MemoryExhausted;
+                break;
+            }
+            goToNextFrame();
+        }
+        if (result.good())
+        {
+            result = dstDataset.insert(dstPerFrameSeq.release());
+        }
+        if (result.good())
+        {
+            result = setConcatenationAttributes(dstDataset, numFramesThisInstance);
+        }
+    }
+    if (result.good())
+    {
+        m_currentInstanceNum++;
+    }
+    return result;
+}
+
+OFCondition ConcatenationCreator::writeNextInstance(const OFFilename& fn)
+{
+    OFCondition result;
+    if (!m_configured)
+    {
+        result = configureCommon();
+        if (result.bad())
+        {
+            return result;
+        }
+    }
+    DcmFileFormat dcmff;
+    result = writeNextInstance(*(dcmff.getDataset()));
+    if (result.good())
+    {
+        result = dcmff.saveFile(fn, EXS_LittleEndianExplicit);
+    }
+    return result;
+}
+
+size_t ConcatenationCreator::getNumInstances()
+{
+    if (!m_configured)
+    {
+        OFCondition result = configureCommon();
+        if (result.bad())
+        {
+            DCMFG_ERROR("Unable to compute number of instances for Concatenation, maybe input not intialized?)");
+            return 0;
+        }
+    }
+    return m_dstNumInstances;
+}
+
+//  --------------------------------- Helpers ------------------------------
+
+OFBool ConcatenationCreator::checkSOPClass(DcmItem& srcDataset)
+{
+    // Check whether the SOP Class is not one of the following:
+    // - Opthalmic Tomography Image Storage
+    // - Opthalmic Optical Coherence Tomography B-Scan Volume Analysis
+    // since the standard forbids to make Concatenations of these.
+    OFString sopClass;
+    srcDataset.findAndGetOFStringArray(DCM_SOPClassUID, sopClass);
+    if (sopClass.empty())
+        return OFFalse;
+
+    if ((sopClass == UID_OphthalmicTomographyImageStorage)
+        || (sopClass == UID_OphthalmicOpticalCoherenceTomographyBscanVolumeAnalysisStorage))
+        return OFFalse;
+
+    return OFTrue;
+}
+
+OFBool ConcatenationCreator::checkColorModel(DcmItem& srcDataset)
+{
+    OFString str;
+    srcDataset.findAndGetOFStringArray(DCM_PhotometricInterpretation, str);
+    if (str.empty())
+    {
+        DCMFG_ERROR("Photometric Interpretation is missing");
+        return OFFalse;
+    }
+    if ((str != "RGB") && (str != "MONOCHROME1") && (str != "MONOCHROME2") && (str != "YBR_FULL"))
+    {
+        DCMFG_ERROR("Photometric Interpretation '" << str << "' not supported");
+        return OFFalse;
+    }
+
+    Uint16 p;
+    if (srcDataset.findAndGetUint16(DCM_PlanarConfiguration, p).good())
+    {
+        if (p != 0)
+        {
+            DCMFG_ERROR("Planar Configuration '" << p << "' not supported (must be 0 if present)");
+            return OFFalse;
+        }
+    }
+
+    return OFTrue;
+}
+
+OFCondition ConcatenationCreator::setConcatenationAttributes(DcmItem& dstDataset, Uint32 numFramesCurrentInstance)
+{
+    OFCondition result = dstDataset.putAndInsertOFStringArray(DCM_ConcatenationUID, m_dstConcatenationUID);
+    if (result.good())
+        result = dstDataset.putAndInsertOFStringArray(DCM_InstanceNumber, m_dstInstanceNumber);
+    if (result.good())
+        result = dstDataset.putAndInsertUint32(DCM_ConcatenationFrameOffsetNumber,
+                                               m_currentInstanceNum * m_dstNumFramesPerInstance);
+    if (result.good())
+        result = dstDataset.putAndInsertOFStringArray(DCM_SOPInstanceUIDOfConcatenationSource, m_srcSOPInstanceUID);
+    if (result.good())
+        result = dstDataset.putAndInsertUint16(DCM_InConcatenationNumber, m_currentInstanceNum + 1 /* first is #1 */);
+    if (result.good())
+    {
+        // safe cast since configureCommon() already checks whether m_dstNumInstances is in Uint16 range
+        result = dstDataset.putAndInsertUint16(DCM_InConcatenationTotalNumber, OFstatic_cast(Uint16, m_dstNumInstances));
+    }
+    if (result.good())
+    {
+
+        OFStringStream ss;
+        ss << numFramesCurrentInstance;
+        result = dstDataset.putAndInsertOFStringArray(DCM_NumberOfFrames, ss.str().c_str());
+    }
+    if (result.good())
+    {
+        char buf[100];
+        dcmGenerateUniqueIdentifier(buf, SITE_INSTANCE_UID_ROOT);
+        result = dstDataset.putAndInsertOFStringArray(DCM_SOPInstanceUID, buf);
+    }
+    return result;
+}
+
+OFCondition ConcatenationCreator::goToNextFrame()
+{
+    // Check whether converter is initialized, and whether frames are left
+    if ((m_currentPerFrameItem == NULL) || (m_currentSrcFrame == m_srcNumFrames))
+    {
+        return FG_EC_NotEnoughFrames;
+    }
+    else
+    {
+        m_currentPerFrameItem = OFstatic_cast(DcmItem*, m_srcPerFrameFG->nextInContainer(m_currentPerFrameItem));
+        m_currentSrcFrame++;
+    }
+    return EC_Normal;
+}
+
+Uint32 ConcatenationCreator::numFramesCurrentDstInstance()
+{
+    Uint32 numFrames = 0;
+    // Calculate last frame number that will be part of "regular" bucket size
+    Uint32 lastRegular = (m_srcNumFrames / m_dstNumFramesPerInstance) * m_dstNumFramesPerInstance - 1;
+    if (m_currentSrcFrame == lastRegular + 1)
+    {
+        numFrames = m_dstNumFramesLastInstance;
+    }
+    else if (m_currentSrcFrame > lastRegular + 1)
+    {
+        return 0;
+    }
+    else
+    {
+        numFrames = m_dstNumFramesPerInstance;
+    }
+    return numFrames;
+}
+
+OFCondition ConcatenationCreator::configureCommon()
+{
+    if (!m_srcDataset || !m_srcPixelData)
+        return EC_IllegalCall;
+
+    // Check for Shared/Per-Frame Functional Group Sequence
+    OFCondition result = m_srcDataset->findAndGetSequence(DCM_PerFrameFunctionalGroupsSequence, m_srcPerFrameFG);
+    if (result.bad())
+        return FG_EC_NoPerFrameFG;
+    if (!m_srcDataset->tagExists(DCM_SharedFunctionalGroupsSequence))
+        return FG_EC_NoSharedFG;
+
+    // Check SOP Class allows Concatenations
+    if (!checkSOPClass(*m_srcDataset))
+        return FG_EC_SOPClassForbidsConcatenations;
+
+    // Check Photometric Interpretation and Planar Configuration
+    if (!checkColorModel(*m_srcDataset))
+        return FG_EC_UnsupportedPixelDataLayout;
+
+    // Check whether number of frames valid in conversion context
+    m_dstNumFramesPerInstance = m_cfgNumFramesPerInstance;
+    Sint32 srcNumFrames       = 0;
+    result                    = m_srcDataset->findAndGetSint32(DCM_NumberOfFrames, srcNumFrames);
+    if (result.bad() || (srcNumFrames <= 1))
+        return FG_EC_NotEnoughFrames;
+    m_srcNumFrames = OFstatic_cast(Uint32, srcNumFrames); // safe since we checked value before
+    if (m_srcNumFrames < m_dstNumFramesPerInstance)
+        return FG_EC_NotEnoughFrames;
+
+    // Remember number of instances to be produced
+    Uint32 u32 = m_srcNumFrames / m_dstNumFramesPerInstance;
+    m_dstNumFramesLastInstance = m_srcNumFrames % m_dstNumFramesPerInstance;
+    if (m_dstNumFramesLastInstance > 0)
+    {
+        u32++;
+    }
+    if (u32 > m_MAX_INSTANCES_PER_CONCATENATION)
+    {
+        DCMFG_ERROR("Too many concatenation instances (" << u32 << "), maximum is " << m_MAX_INSTANCES_PER_CONCATENATION);
+        return FG_EC_InvalidData;
+    }
+    m_dstNumInstances = OFstatic_cast(Uint16, u32); // safe now
+
+    // Check whether pixel data for one instance stays below 4 GB
+    size_t numTotalBytesInstance = m_numBytesFrame * m_dstNumFramesPerInstance;
+    if (numTotalBytesInstance > m_MAX_PIXEL_DATA_LENGTH)
+    {
+        DCMFG_ERROR("Uncompressed pixel data must not exceed " << m_MAX_PIXEL_DATA_LENGTH << "bytes per concatenation instance");
+        return FG_EC_PixelDataDimensionsInvalid;
+    }
+
+    // Check whether number of items in per-frame functional groups is identical to Number of Frames attribute
+    if (m_srcNumFrames != m_srcPerFrameFG->card())
+    {
+        DCMFG_ERROR("Number of Frames attribute does not equal number of items in Per-frame Functional Group Sequence");
+        return FG_EC_NotEnoughFrames;
+    }
+
+    // Check pixel data length correct, i.e. whether there is a sufficient amount of data available
+    Uint16 bitsAlloc, rows, cols;
+    bitsAlloc = rows = cols = 0;
+    m_srcDataset->findAndGetUint16(DCM_BitsAllocated, bitsAlloc);
+    m_srcDataset->findAndGetUint16(DCM_Rows, rows);
+    m_srcDataset->findAndGetUint16(DCM_Columns, cols);
+    if ((rows == 0) || (cols == 0))
+        return FG_EC_PixelDataDimensionsInvalid;
+    // 8, 16 bit and 1 bit (relevant for Segmentation objects) are supported
+    if ((bitsAlloc != 16) && (bitsAlloc != 8) && (bitsAlloc != 1))
+        return FG_EC_PixelDataDimensionsInvalid;
+    if ((bitsAlloc == 1) && (m_dstNumFramesPerInstance % 8 != 0) && (m_dstNumFramesPerInstance * rows * cols % 8 != 0))
+    {
+        DCMFG_ERROR("Can only handle frames per instance (or rows*cols*frames per instance) dividable by 8 for binary "
+                    "segmentations");
+        return EC_InvalidValue;
+    }
+    m_numBytesFrame = rows * cols * bitsAlloc / 8;
+    // In case of 1 bit allocated, tiny images might result in 0 bytes
+    // calculated, so round to 1 byte minimum
+    if (m_numBytesFrame == 0)
+        m_numBytesFrame = 1;
+    if (bitsAlloc <= 8) // 1 or 8 bit
+    {
+        m_VRPixelData = EVR_OB;
+    }
+    else
+    {
+        m_VRPixelData = EVR_OW;
+    }
+    // Store source SOP Instance UID
+    m_srcDataset->findAndGetOFStringArray(DCM_SOPInstanceUID, m_srcSOPInstanceUID);
+    if (m_srcSOPInstanceUID.empty())
+        return EC_InvalidValue; // better code
+
+    //  Create Concatenation UID
+    char buf[65];
+    m_dstConcatenationUID = dcmGenerateUniqueIdentifier(buf, SITE_INSTANCE_UID_ROOT);
+
+    // Set initial context, i.e. initialize for first frame
+    m_currentPerFrameItem = OFstatic_cast(DcmItem*, m_srcPerFrameFG->nextInContainer(NULL));
+    m_currentSrcFrame     = 0;
+
+    m_configured = OFTrue;
+    return result;
+}
diff --git a/dcmfg/libsrc/concatenationloader.cc b/dcmfg/libsrc/concatenationloader.cc
new file mode 100644 (file)
index 0000000..3833ddc
--- /dev/null
@@ -0,0 +1,592 @@
+/*
+ *
+ *  Copyright (C) 2019-2020, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for loading Concatenations
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmdata/dcitem.h"
+#include "dcmtk/dcmdata/dcpixel.h"
+#include "dcmtk/dcmdata/dcuid.h"
+#include "dcmtk/dcmfg/concatenationloader.h"
+#include "dcmtk/dcmfg/fg.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/ofstd/ofstd.h"
+
+//  --------------------------------- Public API ------------------------------
+
+// Constructor
+ConcatenationLoader::ConcatenationLoader()
+    : m_Concats()
+    , m_FailedFiles()
+    , m_ignoreMissingSourceUID(OFFalse)
+    , m_Result(NULL)
+    , m_Frames()
+{
+}
+
+ConcatenationLoader::~ConcatenationLoader()
+{
+    OFMap<OFString, Info*>::iterator it = m_Concats.begin();
+    while (it != m_Concats.end())
+    {
+        delete it->second;
+        m_Concats.erase(it);
+        it = m_Concats.begin();
+    }
+}
+
+void ConcatenationLoader::setIgnoreMissingSourceUID(const OFBool ignore)
+{
+    m_ignoreMissingSourceUID = ignore;
+}
+
+OFCondition ConcatenationLoader::scan(const OFFilename& directory, const OFFilename& pattern, OFBool recursive)
+{
+    OFList<OFFilename> files;
+    size_t results = OFStandard::searchDirectoryRecursively(directory, files, pattern, "", recursive);
+    DCMFG_DEBUG("Found " << results << " for Concatenation scanning");
+    return scan(files);
+}
+
+OFCondition ConcatenationLoader::scan(const OFList<OFFilename>& files)
+{
+    OFCondition result;
+    OFListConstIterator(OFFilename) it = files.begin();
+    size_t count                       = 1;
+    while (it != files.end())
+    {
+        DCMFG_DEBUG("Scanning file #" << count << "/" << files.size());
+        Info info;
+        handleFile(*it, info);
+        it++;
+        count++;
+    }
+
+    doScanFinalChecks();
+    return result;
+}
+
+OFCondition ConcatenationLoader::doScanFinalChecks()
+{
+    ScanResultIt c = m_Concats.begin();
+    while (c != m_Concats.end())
+    {
+        if ((c->second->m_inConcatTotalNumber > 0) && (c->second->m_Files.size() != (c->second->m_inConcatTotalNumber)))
+        {
+            DCMFG_WARN("In-Concatenation Total Number ("
+                       << c->second->m_inConcatTotalNumber << ") does not match number of Instances ("
+                       << c->second->m_Files.size() << ") found for this Concatenation");
+        }
+        c++;
+    }
+    return EC_Normal;
+}
+
+void ConcatenationLoader::handleFile(const OFFilename& file, ConcatenationLoader::Info& info)
+{
+    OFCondition result;
+    DcmFileFormat dcmff;
+    OFString err;
+    Info::Instance inst;
+    result = dcmff.loadFile(file);
+    if (result.good())
+    {
+        DcmDataset* dset = dcmff.getDataset();
+        if (dset)
+        {
+            dset->findAndGetOFStringArray(DCM_SOPInstanceUID, inst.m_sopInstanceUID);
+            dset->findAndGetOFStringArray(DCM_ConcatenationUID, info.m_ConcatenationUID);
+            dset->findAndGetOFStringArray(DCM_SOPInstanceUIDOfConcatenationSource, info.m_SourceUID);
+            dset->findAndGetUint16(DCM_InConcatenationTotalNumber, info.m_inConcatTotalNumber);
+            dset->findAndGetOFStringArray(DCM_PatientID, info.m_PatientID);
+            dset->findAndGetOFStringArray(DCM_StudyInstanceUID, info.m_StudyInstanceUID);
+            dset->findAndGetOFStringArray(DCM_SeriesInstanceUID, info.m_SeriesInstanceUID);
+            dset->findAndGetOFStringArray(DCM_SOPClassUID, info.m_SOPClassUID);
+            dset->findAndGetUint16(DCM_BitsAllocated, info.m_BitsAlloc);
+            dset->findAndGetUint16(DCM_Rows, info.m_Rows);
+            dset->findAndGetUint16(DCM_Columns, info.m_Cols);
+            Sint32 numFrames = 0;
+            if (dset->findAndGetSint32(DCM_NumberOfFrames, numFrames).good())
+            {
+                if (numFrames > 0)
+                    inst.m_NumberOfFrames = OFstatic_cast(Uint32, numFrames);
+            }
+            dset->findAndGetUint16(DCM_InConcatenationNumber, inst.m_InConcatenationNumber);
+            inst.m_Filename = file;
+            checkAndInsertInfo(info, inst, err);
+        }
+        else
+        {
+            err = "No dataset found";
+        }
+    }
+    else
+    {
+        err = "No DICOM file";
+    }
+    if (!err.empty())
+    {
+        m_FailedFiles.push_back(Failure(file, err, inst.m_sopInstanceUID));
+    }
+}
+
+void ConcatenationLoader::checkAndInsertInfo(const ConcatenationLoader::Info& info,
+                                             const ConcatenationLoader::Info::Instance& inst,
+                                             OFString& error)
+{
+    if (!info.m_ConcatenationUID.empty())
+    {
+        OFMap<OFString, Info*>::iterator it = m_Concats.find(info.m_ConcatenationUID);
+        if (it == m_Concats.end())
+        {
+            if ((!info.m_SourceUID.empty() || m_ignoreMissingSourceUID) && (!info.m_StudyInstanceUID.empty())
+                && (!info.m_SeriesInstanceUID.empty()) && (!info.m_SOPClassUID.empty()) && (info.m_BitsAlloc != 0)
+                && (info.m_Rows != 0) && (info.m_Cols != 0) && (inst.m_InConcatenationNumber != 0)
+                && (!inst.m_sopInstanceUID.empty()) && (inst.m_NumberOfFrames != 0))
+            {
+                //  This is a new concatenation, add to list
+                Info* newInfo             = new Info;
+                *newInfo                  = info;
+                newInfo->m_NumTotalFrames = inst.m_NumberOfFrames;
+                newInfo->m_Files.push_back(inst);
+                if (!m_Concats.insert(OFMake_pair(info.m_ConcatenationUID, newInfo)).second)
+                {
+                    error = "Cannot insert into internal data structure";
+                    delete newInfo;
+                }
+            }
+            else
+            {
+                error = "File does not provide all required Concatenation Data";
+            }
+        }
+        else
+        {
+            Info* c = (*it).second;
+            if ((c->m_BitsAlloc == info.m_BitsAlloc) && (c->m_Cols == info.m_Cols) && (c->m_Rows == info.m_Rows)
+                && (c->m_SOPClassUID == info.m_SOPClassUID) && (c->m_SeriesInstanceUID == info.m_SeriesInstanceUID)
+                && (c->m_StudyInstanceUID == info.m_StudyInstanceUID) && emptyOrEqual(c->m_PatientID, info.m_PatientID)
+                && emptyOrEqual(c->m_SourceUID, info.m_SourceUID)
+                && zeroOrEqual(c->m_inConcatTotalNumber, info.m_inConcatTotalNumber)
+                && (c->m_ConcatenationUID == info.m_ConcatenationUID)) /* should always be true, but...  */
+            {
+                //  Add file to this concatenation
+                OFListIterator(ConcatenationLoader::Info::Instance) sortIt = c->m_Files.begin();
+                while (sortIt != c->m_Files.end())
+                {
+                    if ((*sortIt).m_InConcatenationNumber > inst.m_InConcatenationNumber)
+                        break;
+                    sortIt++;
+                }
+                c->m_NumTotalFrames += inst.m_NumberOfFrames;
+                c->m_inConcatTotalNumber = getNotZero(c->m_inConcatTotalNumber, info.m_inConcatTotalNumber);
+                c->m_Files.insert(sortIt, inst);
+            }
+            else
+            {
+                error = "Concatenation Data inconsistent to rest of Concatenation";
+            }
+        }
+    }
+    else
+    {
+        error = "File is not part of Concatenation";
+    }
+}
+
+const ConcatenationLoader::TScanResult& ConcatenationLoader::getInfo()
+{
+    return m_Concats;
+}
+
+const ConcatenationLoader::TScanFailures& ConcatenationLoader::getFailedFiles()
+{
+    return m_FailedFiles;
+}
+
+OFCondition
+ConcatenationLoader::load(const OFString& concatenationUID, DcmDataset* dataset, OFVector<DcmIODTypes::Frame*>& frames)
+{
+    if (dataset == NULL)
+        return EC_IllegalParameter;
+    m_Result = dataset;
+
+    OFCondition result;
+    ScanResultIt concat = m_Concats.find(concatenationUID);
+    if (concat != m_Concats.end())
+    {
+        Info* c = concat->second;
+        if (c || !c->m_Files.empty())
+        {
+            // Create dataset to work with from first concatenation instance
+            DCMFG_DEBUG("Loading Concatenation " << concatenationUID << " from " << c->m_Files.size() << " instances");
+            result = prepareTemplate(*concat->second);
+            if (result.good())
+            {
+                OFListIterator(ConcatenationLoader::Info::Instance) inst = c->m_Files.begin();
+                inst++; // first instance already handled
+                while (result.good() && (inst != c->m_Files.end()))
+                {
+                    DcmFileFormat dcmff;
+                    result = dcmff.loadFile(inst->m_Filename);
+                    if (result.good())
+                    {
+                        if ((*c).m_BitsAlloc == 1)
+                        {
+                            result = extractBinaryFrames(*dcmff.getDataset(), *c, inst->m_NumberOfFrames);
+                        }
+                        else
+                        {
+                            result = extractFrames(*dcmff.getDataset(), *c, inst->m_NumberOfFrames);
+                        }
+
+                        if (result.good())
+                            result = movePerFrameItems(*dcmff.getDataset());
+                    }
+                    inst++;
+                }
+                if (result.good())
+                {
+                    if (result.good())
+                    {
+                        frames = m_Frames;
+                        result = insertDestinationAttributes();
+                    }
+                    else
+                    {
+                        DcmIODUtil::freeContainer(m_Frames);
+                    }
+                }
+            }
+        }
+        else
+        {
+            result = EC_InternalError;
+        }
+    }
+
+    return result;
+}
+
+OFCondition ConcatenationLoader::prepareTemplate(ConcatenationLoader::Info& firstInstance)
+{
+    DcmFileFormat dcmff;
+    OFCondition result = dcmff.loadFile(firstInstance.m_Files.front().m_Filename);
+    if (result.good())
+    {
+        *m_Result = *dcmff.getDataset();
+        OFString srcUID;
+        result = m_Result->findAndGetOFStringArray(DCM_SOPInstanceUIDOfConcatenationSource, srcUID);
+        if (result.bad() && m_ignoreMissingSourceUID)
+            result = EC_Normal;
+        if (result.good())
+            result = deleteConcatAttributes(*m_Result);
+        if (result.good())
+            result = m_Result->putAndInsertOFStringArray(DCM_SOPInstanceUID, srcUID);
+        if (result.good())
+        {
+            result = extractFrames(*m_Result, firstInstance, firstInstance.m_Files.front().m_NumberOfFrames);
+            m_Result->findAndDeleteElement(DCM_PixelData);
+        }
+    }
+    return result;
+}
+
+OFCondition ConcatenationLoader::deleteConcatAttributes(DcmItem& item)
+{
+    item.findAndDeleteElement(DCM_ConcatenationUID);
+    item.findAndDeleteElement(DCM_InConcatenationNumber);
+    item.findAndDeleteElement(DCM_InConcatenationTotalNumber);
+    item.findAndDeleteElement(DCM_SOPInstanceUIDOfConcatenationSource);
+    item.findAndDeleteElement(DCM_ConcatenationFrameOffsetNumber);
+    item.findAndDeleteElement(DCM_NumberOfFrames);
+    item.findAndDeleteElement(DCM_ContentDate);
+    item.findAndDeleteElement(DCM_ContentTime);
+    item.findAndDeleteElement(DCM_SOPInstanceUID);
+    return EC_Normal;
+}
+
+OFCondition ConcatenationLoader::extractFrames(DcmItem& item, Info& info, const Uint32 numFrames)
+{
+    const Uint8* pixData = NULL;
+    OFCondition result   = item.findAndGetUint8Array(DCM_PixelData, pixData);
+    if (result.good() && pixData)
+    {
+        size_t bytes_per_frame = 0;
+        result                 = computeBytesPerFrame(info.m_Rows, info.m_Cols, info.m_BitsAlloc, bytes_per_frame);
+        if (result.good())
+        {
+            const Uint8* ptr = pixData;
+            for (Uint32 f = 0; f < numFrames; f++)
+            {
+                DcmIODTypes::Frame* frame = new DcmIODTypes::Frame();
+                if (frame)
+                {
+                    frame->length  = bytes_per_frame;
+                    frame->pixData = new Uint8[frame->length];
+                    if (frame->pixData)
+                    {
+                        memcpy(frame->pixData, ptr, frame->length);
+                        ptr += frame->length;
+                        m_Frames.push_back(frame);
+                    }
+                    else
+                    {
+                        result = EC_MemoryExhausted;
+                    }
+                }
+                else
+                {
+                    result = EC_MemoryExhausted;
+                }
+            }
+        }
+    }
+    else
+    {
+        result = FG_EC_PixelDataMissing;
+    }
+    return result;
+}
+
+OFCondition ConcatenationLoader::extractBinaryFrames(DcmItem& item, Info& info, const Uint32 numFrames)
+{
+    Uint8* pixData          = NULL;
+    DcmElement* pixDataElem = NULL;
+    OFCondition result      = item.findAndGetElement(DCM_PixelData, pixDataElem);
+    if (result.good())
+        result = pixDataElem->getUint8Array(pixData);
+    if (result.good() && pixData)
+    {
+        result = DcmIODUtil::extractBinaryFrames(pixData, numFrames, info.m_Rows * info.m_Cols, m_Frames);
+    }
+    else
+    {
+        result = FG_EC_PixelDataMissing;
+    }
+    return result;
+}
+
+OFCondition ConcatenationLoader::computeBytesPerFrame(const Uint16 rows,
+                                                      const Uint16 cols,
+                                                      const Uint16 bitsAlloc,
+                                                      size_t& bytes_per_frame)
+{
+    // Usually bytes of one frame simply computes using cols * rows * num bytes per pixel.
+    // This is only different if bits allocated equals 1, which can happen
+    // for binary segmentations or black and white secondary capture objects
+    // (second SC generation).
+    // Other values than Bits Allocated 16 or 8 are not supported.
+    bytes_per_frame = bitsAlloc * cols * rows;
+    if ((bitsAlloc == 16) || (bitsAlloc == 8))
+    {
+        // result in rows * cols * bytes per frame
+        bytes_per_frame = bytes_per_frame / 8;
+    }
+    else if (bitsAlloc == 1)
+    {
+        // results in rows * cols / 8 if rows*cols is dividable by 8,
+        // otherwise rows * cols / 8 +1 (extra byte)
+        OFBool remainder = (bytes_per_frame % 8 != 0) ? OFTrue: OFFalse;
+        bytes_per_frame  = bytes_per_frame / 8;
+        if (remainder)
+        {
+            bytes_per_frame++;
+        }
+    }
+    else
+    {
+        DCMFG_ERROR("Bits Allocated=" << bitsAlloc << " not supported, must be 1, 8 or 16");
+        return FG_EC_UnsupportedPixelDataLayout;
+    }
+    return EC_Normal;
+}
+
+OFCondition ConcatenationLoader::movePerFrameItems(DcmItem& item)
+{
+    OFCondition result;
+    DcmSequenceOfItems* srcPerFrame = NULL;
+    DcmSequenceOfItems* dstPerFrame = NULL;
+    m_Result->findAndGetSequence(DCM_PerFrameFunctionalGroupsSequence, dstPerFrame);
+    if (item.findAndGetSequence(DCM_PerFrameFunctionalGroupsSequence, srcPerFrame).good() && dstPerFrame)
+    {
+        while (result.good() && (srcPerFrame->card() != 0))
+        {
+            result = dstPerFrame->append(srcPerFrame->remove(OFstatic_cast(unsigned long, 0)));
+        }
+    }
+    return result;
+}
+
+OFCondition ConcatenationLoader::insertDestinationAttributes()
+{
+    Info* info   = m_Concats.begin()->second;
+    OFString uid = info->m_SourceUID;
+    if (uid.empty())
+    {
+        char buf[100];
+        dcmGenerateUniqueIdentifier(buf, SITE_INSTANCE_UID_ROOT);
+        uid = buf;
+        DCMFG_WARN("SOP Instance UID of Concatentation Source (0020,0242)​ not set, created new SOP Instance UID "
+                   << uid);
+    }
+    OFCondition result = m_Result->putAndInsertOFStringArray(DCM_SOPInstanceUID, uid);
+    if (result.good())
+    {
+        OFStringStream s;
+        s << info->m_NumTotalFrames;
+        result = m_Result->putAndInsertOFStringArray(DCM_NumberOfFrames, s.str().c_str());
+    }
+    if (result.good())
+    {
+        OFDate date;
+        date.setCurrentDate();
+        OFString tempstr;
+        date.getISOFormattedDate(tempstr, OFFalse /* no delimiters */);
+        result = m_Result->putAndInsertOFStringArray(DCM_ContentDate, tempstr);
+        if (result.good())
+        {
+            OFTime time;
+            time.setCurrentTime();
+            time.getISOFormattedTime(tempstr, OFTrue /* include seconds */, OFFalse, OFFalse, OFFalse);
+            result = m_Result->putAndInsertOFStringArray(DCM_ContentTime, tempstr);
+        }
+    }
+    return result;
+}
+
+OFBool ConcatenationLoader::zeroOrEqual(const size_t num1, const size_t num2)
+{
+    if (num1 == num2)
+        return OFTrue;
+    if ((num1 == 0) || (num2 == 0))
+        return OFTrue;
+    return OFFalse;
+}
+
+OFBool ConcatenationLoader::emptyOrEqual(const OFString& str1, const OFString& str2)
+{
+    if (str1 == str2)
+        return OFTrue;
+    if (str1.empty() || str2.empty())
+        return OFTrue;
+    return OFFalse;
+}
+
+template <typename T>
+T ConcatenationLoader::getNotZero(const T num1, const T num2)
+{
+    if (num1 != 0)
+        return num1;
+    return num2;
+}
+
+ConcatenationLoader::Info::Info()
+    : m_Files()
+    , m_FileConatenationSource()
+    , m_ConcatenationUID()
+    , m_SourceUID()
+    , m_inConcatTotalNumber(0)
+    , m_NumTotalFrames(0)
+    , m_PatientID()
+    , m_StudyInstanceUID()
+    , m_SeriesInstanceUID()
+    , m_SOPClassUID()
+    , m_BitsAlloc(0)
+    , m_Rows(0)
+    , m_Cols(0)
+{
+}
+
+ConcatenationLoader::Info& ConcatenationLoader::Info::operator=(const ConcatenationLoader::Info& rhs)
+{
+    this->m_FileConatenationSource   = rhs.m_FileConatenationSource;
+    this->m_ConcatenationUID         = rhs.m_ConcatenationUID;
+    this->m_SourceUID                = rhs.m_SourceUID;
+    this->m_NumTotalFrames           = rhs.m_NumTotalFrames;
+    this->m_inConcatTotalNumber      = rhs.m_inConcatTotalNumber;
+    this->m_PatientID                = rhs.m_PatientID;
+    this->m_StudyInstanceUID         = rhs.m_StudyInstanceUID;
+    this->m_SeriesInstanceUID        = rhs.m_SeriesInstanceUID;
+    this->m_SOPClassUID              = rhs.m_SOPClassUID;
+    this->m_BitsAlloc                = rhs.m_BitsAlloc;
+    this->m_Rows                     = rhs.m_Rows;
+    this->m_Cols                     = rhs.m_Cols;
+    OFListConstIterator(Instance) it = rhs.m_Files.begin();
+    while (it != rhs.m_Files.end())
+    {
+        this->m_Files.push_back(*it);
+        it++;
+    }
+    return *this;
+}
+
+ConcatenationLoader::Info::Info(const ConcatenationLoader::Info& rhs)
+{
+    if (&rhs == this)
+        return;
+
+    *this = rhs;
+}
+
+void ConcatenationLoader::Info::print(OFStringStream& out)
+{
+    out << "Concatenation UID*           : " << m_ConcatenationUID << OFendl;
+    out << "  SOP Class UID*             : " << m_SOPClassUID << OFendl;
+    out << "  Concatentation Source UID* : " << m_SourceUID << OFendl;
+    out << "  Concatentation Source File : " << m_FileConatenationSource << OFendl;
+    out << "  Number of Frames (computed): " << m_NumTotalFrames << OFendl;
+    out << "  In-conc. Total Number      : " << m_inConcatTotalNumber << OFendl;
+    out << "  Patient ID                 : " << m_PatientID << OFendl;
+    out << "  Study Instance UID*        : " << m_StudyInstanceUID << OFendl;
+    out << "  Series Instance UID*       : " << m_SeriesInstanceUID << OFendl;
+    out << "  Bits Allocated*            : " << m_BitsAlloc << OFendl;
+    out << "  Rows*                      : " << m_Rows << OFendl;
+    out << "  Columns*                   : " << m_Cols << OFendl;
+    out << "  Files: " << OFendl;
+    OFListIterator(Instance) f = m_Files.begin();
+    size_t count               = 1;
+    while (f != m_Files.end())
+    {
+        out << "    " << count << ". " << (*f).m_Filename << OFendl;
+        out << "    SOP Instance UID: " << (*f).m_sopInstanceUID << OFendl;
+        out << "    Number of Frames: " << (*f).m_NumberOfFrames << OFendl;
+        out << "    In-Concatenation Frame Offset Number: " << (*f).m_InConcatenationNumber << OFendl;
+        f++;
+        count++;
+    }
+}
+
+ConcatenationLoader::Info::~Info()
+{
+}
+
+ConcatenationLoader::Info::Instance::Instance()
+    : m_Filename()
+    , m_sopInstanceUID()
+    , m_NumberOfFrames(0)
+    , m_InConcatenationNumber(0)
+{
+}
+
+ConcatenationLoader::Info::Instance::~Instance()
+{
+}
index b97d2f1975bd9e9c247c805485c095ef60c7f23e..401a1f23decb3c8e7065f3a5a2cfe6f03ffe23f9 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2017, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  */
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmfg/fg.h"
 
+#include "dcmtk/dcmfg/fg.h"
 
 FunctionalGroups::FunctionalGroups()
-: m_groups()
+    : m_groups()
 {
 }
 
-
 FunctionalGroups::~FunctionalGroups()
 {
-  clear();
+    clear();
 }
 
-
 void FunctionalGroups::clear()
 {
-  // free memory of underlying map
-  while ( m_groups.size() > 0)
-  {
-    FunctionalGroups::iterator it = m_groups.begin();
-    FGBase* fg = (*it).second;
-    m_groups.erase(it);
-    delete fg;
-  }
+    // free memory of underlying map
+    while (m_groups.size() > 0)
+    {
+        FunctionalGroups::iterator it = m_groups.begin();
+        FGBase* fg                    = (*it).second;
+        m_groups.erase(it);
+        delete fg;
+    }
 }
 
-
-
 FGBase* FunctionalGroups::find(const DcmFGTypes::E_FGType fgType)
 {
-  FGBase* group = NULL;
-  FunctionalGroups::iterator it = m_groups.find(fgType);
-  FunctionalGroups::iterator done = m_groups.end();
-  if ( it != done)
-  {
-    group = (*it).second;
-  }
-  return group;
+    FGBase* group                   = NULL;
+    FunctionalGroups::iterator it   = m_groups.find(fgType);
+    FunctionalGroups::iterator done = m_groups.end();
+    if (it != done)
+    {
+        group = (*it).second;
+    }
+    return group;
 }
 
-
 FunctionalGroups::iterator FunctionalGroups::begin()
 {
-  return  m_groups.begin();
+    return m_groups.begin();
 }
 
-
 FunctionalGroups::iterator FunctionalGroups::end()
 {
-  return m_groups.end();
+    return m_groups.end();
 }
 
-
 FunctionalGroups::const_iterator FunctionalGroups::begin() const
 {
-  return m_groups.begin();
+    return m_groups.begin();
 }
 
-
 FunctionalGroups::const_iterator FunctionalGroups::end() const
 {
-  return m_groups.end();
+    return m_groups.end();
 }
 
-
-OFCondition FunctionalGroups::insert(FGBase* group,
-                                     const OFBool replaceOld)
+OFCondition FunctionalGroups::insert(FGBase* group, const OFBool replaceOld)
 {
-  if (group == NULL)
-    return EC_IllegalParameter;
+    if (group == NULL)
+        return EC_IllegalParameter;
 
-  OFCondition result;
-  FGBase* existing = find(group->getType());
-  if (existing)
-  {
-    if (replaceOld)
-    {
-      DCMFG_DEBUG("Replacing existing functional group");
-      delete remove(group->getType());
-    }
-    else
-    {
-      DCMFG_ERROR("Cannot insert functional group: Group does already exist");
-      result = FG_EC_DoubledFG;
-    }
-  }
-  if (result.good())
-  {
-    if ( (m_groups.insert(OFMake_pair(group->getType(), group)).second) )
+    OFCondition result;
+    FGBase* existing = find(group->getType());
+    if (existing)
     {
-      DCMFG_DEBUG("Functional group successfully inserted: " << DcmFGTypes::FGType2OFString(group->getType()));
+        if (replaceOld)
+        {
+            DCMFG_DEBUG("Replacing existing functional group");
+            delete remove(group->getType());
+        }
+        else
+        {
+            DCMFG_ERROR("Cannot insert functional group: Group does already exist");
+            result = FG_EC_DoubledFG;
+        }
     }
-    else
+    if (result.good())
     {
-      DCMFG_ERROR("Cannot insert functional group: Internal error");
-      result = FG_EC_CouldNotInsertFG;
+        if ((m_groups.insert(OFMake_pair(group->getType(), group)).second))
+        {
+            DCMFG_DEBUG("Functional group successfully inserted: " << DcmFGTypes::FGType2OFString(group->getType()));
+        }
+        else
+        {
+            DCMFG_ERROR("Cannot insert functional group: Internal error");
+            result = FG_EC_CouldNotInsertFG;
+        }
     }
-  }
-  return result;
+    return result;
 }
 
-
 FGBase* FunctionalGroups::remove(const DcmFGTypes::E_FGType fgType)
 {
-  FGBase* fg = find(fgType);
-  m_groups.erase(fgType);
-  return fg;
+    FGBase* fg = find(fgType);
+    m_groups.erase(fgType);
+    return fg;
 }
-
index d382e054b5642256bab398dd5a5217978f3137df..e2e47b46f09639e88ea94cf284cab4eda241b2e4 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  */
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmfg/fgbase.h"
+
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgbase.h"
 #include "dcmtk/dcmiod/iodcommn.h" // for static element helpers
 
-
-FGBase::FGBase(const DcmFGTypes::E_FGType fgType) :
-  m_fgType(fgType)
+FGBase::FGBase(const DcmFGTypes::E_FGType fgType)
+    : m_fgType(fgType)
 {
 }
 
-
 FGBase::~FGBase()
 {
 }
 
-
 void FGBase::clearData()
 {
 }
 
-
 DcmFGTypes::E_FGType FGBase::getType() const
 {
-  return m_fgType;
+    return m_fgType;
 }
 
-
 DcmFGTypes::E_FGSharedType FGBase::getSharedType() const
 {
-  return DcmFGTypes::EFGS_UNKNOWN;
+    return DcmFGTypes::EFGS_UNKNOWN;
 }
 
-
 int FGBase::compare(const FGBase& rhs) const
 {
-  // Check for equality from FGBase' point of view
+    // Check for equality from FGBase' point of view
 
-  // Same objects?
-  if (this == &rhs)
-    return 0;
+    // Same objects?
+    if (this == &rhs)
+        return 0;
 
-  // Type identical?
-  if ( this->getType() != rhs.getType() )
-    return -1;
+    // Type identical?
+    if (this->getType() != rhs.getType())
+        return -1;
 
-  // This is all we can do
-  return 0;
+    // This is all we can do
+    return 0;
 }
 
-
 OFCondition FGBase::getItemFromFGSequence(DcmItem& source,
                                           const DcmTagKey& seqKey,
                                           const long unsigned int itemNum,
                                           DcmItem*& result)
 {
-  result = NULL;
-  DcmSequenceOfItems *seq = NULL;
-  if (source.findAndGetSequence(seqKey, seq).bad())
-  {
-    DCMFG_ERROR("Functional Group Sequence does not exist: " << seqKey << " (" << DcmFGTypes::tagKey2FGType(seqKey) << ")");
-    return EC_TagNotFound;
-  }
-  result = seq->getItem(itemNum);
-  if (result == NULL)
-  {
-    DCMFG_DEBUG("Functional Group Sequence " << seqKey << " (" << DcmFGTypes::tagKey2FGType(seqKey) << ") does not have " << itemNum-1 << " items");
-    return FG_EC_NotEnoughItems;
-  }
-  return EC_Normal;
+    result                  = NULL;
+    DcmSequenceOfItems* seq = NULL;
+    if (source.findAndGetSequence(seqKey, seq).bad())
+    {
+        DCMFG_ERROR("Functional Group Sequence does not exist: " << seqKey << " (" << DcmFGTypes::tagKey2FGType(seqKey)
+                                                                 << ")");
+        return EC_TagNotFound;
+    }
+    result = seq->getItem(itemNum);
+    if (result == NULL)
+    {
+        DCMFG_DEBUG("Functional Group Sequence " << seqKey << " (" << DcmFGTypes::tagKey2FGType(seqKey)
+                                                 << ") does not have " << itemNum - 1 << " items");
+        return FG_EC_NotEnoughItems;
+    }
+    return EC_Normal;
 }
 
+OFCondition FGBase::getNumItemsFromFGSequence(DcmItem& source, const DcmTagKey& seqKey, unsigned long& result)
+{
+    result                  = 0;
+    DcmSequenceOfItems* seq = NULL;
+    if (source.findAndGetSequence(seqKey, seq).bad())
+    {
+        DCMFG_ERROR("Functional Group Sequence does not exist: " << seqKey << " (" << DcmFGTypes::tagKey2FGType(seqKey)
+                                                                 << ")");
+        return EC_TagNotFound;
+    }
+    result = seq->card();
+    return EC_Normal;
+}
 
 OFCondition FGBase::createNewFGSequence(DcmItem& destination,
                                         const DcmTagKey& seqKey,
-                                        const long unsigned int numItems,
+                                        const unsigned long numItems,
                                         DcmItem*& firstItem)
 {
-  firstItem = NULL;
-  OFCondition result = destination.insertEmptyElement(seqKey, OFTrue /* replace old */);
-  if (result.bad())
-  {
-    DCMFG_ERROR("Could not create Functional Group with sequence " << seqKey << " (" << DcmFGTypes::tagKey2FGType(seqKey) << ")");
-    return FG_EC_CouldNotInsertFG;
-  }
-  DcmItem* dummy =NULL;
-  result = destination.findOrCreateSequenceItem(seqKey, dummy, numItems );
-  if (result.bad())
-  {
-    // clean up
-    destination.findAndDeleteElement(seqKey);
-    DCMFG_ERROR("Could not create " << numItems << " items in Functional Group with sequence " << seqKey << " (" << DcmFGTypes::tagKey2FGType(seqKey) << ")");
-    return FG_EC_CouldNotInsertFG;
-  }
-  destination.findOrCreateSequenceItem(seqKey, firstItem, 0);
-  return EC_Normal;
-}
+    if (numItems > OFstatic_cast(unsigned long, OFnumeric_limits<signed long>::max()))
+        return EC_IllegalParameter;
 
+    firstItem          = NULL;
+    OFCondition result = destination.insertEmptyElement(seqKey, OFTrue /* replace old */);
+    if (result.bad())
+    {
+        DCMFG_ERROR("Could not create Functional Group with sequence " << seqKey << " ("
+                                                                       << DcmFGTypes::tagKey2FGType(seqKey) << ")");
+        return FG_EC_CouldNotInsertFG;
+    }
+    DcmItem* dummy = NULL;
+    result         = destination.findOrCreateSequenceItem(seqKey, dummy, OFstatic_cast(signed long, numItems));
+    if (result.bad())
+    {
+        // clean up
+        destination.findAndDeleteElement(seqKey);
+        DCMFG_ERROR("Could not create " << numItems << " items in Functional Group with sequence " << seqKey << " ("
+                                        << DcmFGTypes::tagKey2FGType(seqKey) << ")");
+        return FG_EC_CouldNotInsertFG;
+    }
+    destination.findOrCreateSequenceItem(seqKey, firstItem, 0);
+    return EC_Normal;
+}
 
 // ------------------ class FGUnknown ------------------------------------
 
-
-FGUnknown::FGUnknown(const DcmTagKey& seqStartTag,
-                     const DcmFGTypes::E_FGSharedType sharedType) :
-  FGBase(DcmFGTypes::EFG_UNKNOWN),
-  m_seqStartTag(seqStartTag),
-  m_fgSequence(NULL),
-  m_sharedType(sharedType)
+FGUnknown::FGUnknown(const DcmTagKey& seqStartTag, const DcmFGTypes::E_FGSharedType sharedType)
+    : FGBase(DcmFGTypes::EFG_UNKNOWN)
+    , m_seqStartTag(seqStartTag)
+    , m_fgSequence(NULL)
+    , m_sharedType(sharedType)
 {
 }
 
-FGUnknown::FGUnknown(const FGUnknown& rhs) :
-    FGBase(DcmFGTypes::EFG_UNKNOWN),
-    m_seqStartTag(rhs.m_seqStartTag),
-    m_fgSequence(OFstatic_cast(DcmSequenceOfItems*, rhs.m_fgSequence->clone())),
-    m_sharedType(rhs.m_sharedType)
+FGUnknown::FGUnknown(const FGUnknown& rhs)
+    : FGBase(DcmFGTypes::EFG_UNKNOWN)
+    , m_seqStartTag(rhs.m_seqStartTag)
+    , m_fgSequence(OFstatic_cast(DcmSequenceOfItems*, rhs.m_fgSequence->clone()))
+    m_sharedType(rhs.m_sharedType)
 {
 }
 
-
-FGUnknown & FGUnknown::operator=(const FGUnknown& rhs)
+FGUnknown& FGUnknown::operator=(const FGUnknown& rhs)
 {
     m_seqStartTag = rhs.m_seqStartTag;
-    m_fgSequence = OFstatic_cast(DcmSequenceOfItems*, rhs.m_fgSequence->clone());
-    m_sharedType = rhs.m_sharedType;
+    m_fgSequence  = OFstatic_cast(DcmSequenceOfItems*, rhs.m_fgSequence->clone());
+    m_sharedType  = rhs.m_sharedType;
     return *this;
 }
 
-
 void FGUnknown::clearData()
 {
-  if (m_fgSequence != NULL)
-  {
-    delete m_fgSequence;
-    m_fgSequence = NULL;
-  }
+    if (m_fgSequence != NULL)
+    {
+        delete m_fgSequence;
+        m_fgSequence = NULL;
+    }
 }
 
-
 OFCondition FGUnknown::read(DcmItem& item)
 {
-  // clear old data
-  clearData();
-  OFCondition result = item.findAndGetSequence(m_seqStartTag, m_fgSequence, OFFalse /* no depth search */, OFTrue /* create copy! */);
-  if ( result.bad() )
-  {
-    if (m_fgSequence != NULL)
-      delete m_fgSequence;
-    m_fgSequence = NULL;
-  }
-  return result;
+    // clear old data
+    clearData();
+    OFCondition result = item.findAndGetSequence(
+        m_seqStartTag, m_fgSequence, OFFalse /* no depth search */, OFTrue /* create copy! */);
+    if (result.bad())
+    {
+        if (m_fgSequence != NULL)
+            delete m_fgSequence;
+        m_fgSequence = NULL;
+    }
+    return result;
 }
 
-
 OFCondition FGUnknown::write(DcmItem& item)
 {
-  return item.insert(new DcmSequenceOfItems(*m_fgSequence), OFTrue /* replace old! */);
+    return item.insert(new DcmSequenceOfItems(*m_fgSequence), OFTrue /* replace old! */);
 }
 
-
 OFCondition FGUnknown::check() const
 {
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 int FGUnknown::compare(const FGBase& rhs) const
 {
-  int result = FGBase::compare(rhs);
-  if (result == 0)
-  {
-    const FGUnknown* myRhs = OFstatic_cast(const FGUnknown*, &rhs);
-
-    // Compare all elements
-    if (m_seqStartTag == myRhs->m_seqStartTag)
+    int result = FGBase::compare(rhs);
+    if (result == 0)
     {
-      if (m_fgSequence && myRhs->m_fgSequence)
-      {
-        result = m_fgSequence->compare( *(myRhs->m_fgSequence) );
-      }
-      else if (!m_fgSequence && !myRhs->m_fgSequence) // if both are not set, objects are still equal
-      {
-        result = 0;
-      }
-      else if (m_fgSequence)
-      {
-        result = 1; // this object is bigger (more information)
-      }
-      else if (myRhs->m_fgSequence)
-      {
-        result = -1; // rhs object is bigger (more information)
-      }
+        const FGUnknown* myRhs = OFstatic_cast(const FGUnknown*, &rhs);
+
+        // Compare all elements
+        if (m_seqStartTag == myRhs->m_seqStartTag)
+        {
+            if (m_fgSequence && myRhs->m_fgSequence)
+            {
+                result = m_fgSequence->compare(*(myRhs->m_fgSequence));
+            }
+            else if (!m_fgSequence && !myRhs->m_fgSequence) // if both are not set, objects are still equal
+            {
+                result = 0;
+            }
+            else if (m_fgSequence)
+            {
+                result = 1; // this object is bigger (more information)
+            }
+            else if (myRhs->m_fgSequence)
+            {
+                result = -1; // rhs object is bigger (more information)
+            }
+        }
+        else
+        {
+            result = (m_seqStartTag < myRhs->m_seqStartTag) ? -1 : 1;
+        }
     }
-    else
-    {
-      result = (m_seqStartTag < myRhs->m_seqStartTag) ? -1 : 1;
-    }
-  }
 
-  return result;
+    return result;
 }
 
-
 FGUnknown::~FGUnknown()
 {
-  clearData();
+    clearData();
 }
 
-
 FGBase* FGUnknown::clone() const
 {
-  FGUnknown* copy = new FGUnknown(this->m_seqStartTag);
-  if (copy)
-  {
-    *(copy->m_fgSequence) = *(this->m_fgSequence);
-  }
-  return copy;
+    FGUnknown* copy = new FGUnknown(this->m_seqStartTag);
+    if (copy)
+    {
+        *(copy->m_fgSequence) = *(this->m_fgSequence);
+    }
+    return copy;
 }
diff --git a/dcmfg/libsrc/fgctacquisitiondetails.cc b/dcmfg/libsrc/fgctacquisitiondetails.cc
new file mode 100644 (file)
index 0000000..22f5253
--- /dev/null
@@ -0,0 +1,398 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT Acquisition Details Functional Group
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgctacquisitiondetails.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/dcmiod/iodutil.h"
+
+// Constructor
+FGCTAcquisitionDetails::FGCTAcquisitionDetails()
+    : FGBase(DcmFGTypes::EFG_CTACQUISITIONDETAILS)
+    , m_Items()
+{
+}
+
+FGCTAcquisitionDetails::~FGCTAcquisitionDetails()
+{
+    clearData();
+}
+
+FGBase* FGCTAcquisitionDetails::clone() const
+{
+    OFunique_ptr<FGCTAcquisitionDetails> copy(new FGCTAcquisitionDetails());
+    if (copy)
+    {
+        if (DcmIODUtil::copyContainer(this->m_Items, copy->m_Items).good())
+        {
+            return copy.release();
+        }
+    }
+    return OFnullptr;
+}
+
+void FGCTAcquisitionDetails::clearData()
+{
+    DcmIODUtil::freeContainer(m_Items);
+    m_Items.clear();
+}
+
+OFCondition FGCTAcquisitionDetails::check() const
+{
+    // Maybe add checks later
+    return EC_Normal;
+}
+
+/// Read CT Acquisition Details Sequence from given item
+OFCondition FGCTAcquisitionDetails::read(DcmItem& item)
+{
+    clearData();
+    DcmItem* seqItem       = NULL;
+    unsigned long numItems = 0;
+    OFCondition result     = getNumItemsFromFGSequence(item, DCM_CTAcquisitionDetailsSequence, numItems);
+    if (result.bad())
+        return result;
+
+    for (unsigned long num = 0; num < numItems; num++)
+    {
+        if (getItemFromFGSequence(item, DCM_CTAcquisitionDetailsSequence, num, seqItem).good())
+        {
+            FGCTAcquisitionDetailsItem* newItem = new FGCTAcquisitionDetailsItem();
+            newItem->read(*seqItem);
+            m_Items.push_back(newItem);
+        }
+    }
+    return EC_Normal;
+}
+
+/// Write CT Acquisition Detail Sequence into given item
+OFCondition FGCTAcquisitionDetails::write(DcmItem& item)
+{
+    OFCondition result = check();
+    if (result.good())
+    {
+        DcmIODUtil::writeSubSequence(
+            result, DCM_CTAcquisitionDetailsSequence, m_Items, item, "1-n", "2", "CTAcquisitionDetailsMacro");
+    }
+
+    return result;
+}
+
+int FGCTAcquisitionDetails::compare(const FGBase& rhs) const
+{
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
+
+    FGCTAcquisitionDetails* myRhs
+        = OFconst_cast(FGCTAcquisitionDetails*, (OFstatic_cast(const FGCTAcquisitionDetails*, &rhs)));
+    if (!myRhs)
+        return -1;
+
+    // Compare all items
+    return DcmIODUtil::compareContainer(this->m_Items, myRhs->m_Items);
+}
+
+OFVector<FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem*>& FGCTAcquisitionDetails::getCTAcquisitionDetailsItems()
+{
+    return m_Items;
+}
+
+// ------------ Class FGCTAcquisitionDetailsItem::FGCTAcquisitionDetailsItem -------------
+
+FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::FGCTAcquisitionDetailsItem()
+    : m_ReferencedPathIndex(DCM_ReferencedPathIndex)
+    , m_RotationDirection(DCM_RotationDirection)
+    , m_RevolutionTime(DCM_RevolutionTime)
+    , m_SingleCollimationWidth(DCM_SingleCollimationWidth)
+    , m_TotalCollimationWidth(DCM_TotalCollimationWidth)
+    , m_TableHeight(DCM_TableHeight)
+    , m_GantryDetectorTilt(DCM_GantryDetectorTilt)
+    , m_DataCollectionDiameter(DCM_DataCollectionDiameter)
+{
+}
+
+FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::~FGCTAcquisitionDetailsItem()
+{
+    // Nothing to do
+}
+
+// --- get() functionality ---
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::check() const
+{
+    // Maybe add checks later
+    return EC_Normal;
+}
+
+void FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::clearData()
+{
+    m_DataCollectionDiameter.clear();
+    m_GantryDetectorTilt.clear();
+    m_ReferencedPathIndex.clear();
+    m_RevolutionTime.clear();
+    m_RotationDirection.clear();
+    m_SingleCollimationWidth.clear();
+    m_TableHeight.clear();
+    m_TotalCollimationWidth.clear();
+}
+
+int FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::compare(
+    const FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem& rhs) const
+{
+    FGCTAcquisitionDetailsItem* myRhs = OFconst_cast(FGCTAcquisitionDetailsItem*, &rhs);
+    if (!myRhs)
+        return -1;
+
+    // Compare all elements
+    int result = m_DataCollectionDiameter.compare(myRhs->m_DataCollectionDiameter);
+    if (result == 0)
+        result = m_GantryDetectorTilt.compare(myRhs->m_GantryDetectorTilt);
+    if (result == 0)
+        result = m_ReferencedPathIndex.compare(myRhs->m_ReferencedPathIndex);
+    if (result == 0)
+        result = m_RevolutionTime.compare(myRhs->m_RevolutionTime);
+    if (result == 0)
+        result = m_RotationDirection.compare(myRhs->m_RotationDirection);
+    if (result == 0)
+        result = m_SingleCollimationWidth.compare(myRhs->m_SingleCollimationWidth);
+    if (result == 0)
+        result = m_TableHeight.compare(myRhs->m_TableHeight);
+    if (result == 0)
+        result = m_TotalCollimationWidth.compare(myRhs->m_TotalCollimationWidth);
+    return result;
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::getDataCollectionDiameter(Float64& value,
+                                                                                          const unsigned long pos)
+{
+    return m_DataCollectionDiameter.getFloat64(value, pos);
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::getGantryDetectorTilt(Float64& value,
+                                                                                      const unsigned long pos)
+{
+    return m_GantryDetectorTilt.getFloat64(value, pos);
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::getReferencedPathIndex(OFVector<Uint16>& values)
+{
+    return DcmIODUtil::getUint16ValuesFromElement(m_ReferencedPathIndex, values);
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::getReferencedPathIndex(Uint16& value,
+                                                                                       const unsigned long pos)
+{
+    return m_ReferencedPathIndex.getUint16(value, pos);
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::getRevolutionTime(Float64& value,
+                                                                                  const unsigned long pos)
+{
+    return m_RevolutionTime.getFloat64(value, pos);
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::getRotationDirection(
+    FGCTAcquisitionDetails::E_RotationDirection& value, const long pos)
+{
+    OFString str;
+    DcmIODUtil::getStringValueFromElement(m_RotationDirection, str, pos);
+    value = rotaDir2Enum(str);
+    if ((value != FGCTAcquisitionDetails::E_RotationDirection_Empty)
+        && (value != FGCTAcquisitionDetails::E_RotationDirection_Invalid))
+        return EC_Normal;
+    else
+        return EC_InvalidValue;
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::getRotationDirection(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_RotationDirection, value, pos);
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::getSingleCollimationWidth(Float64& value,
+                                                                                          const unsigned long pos)
+{
+    return m_SingleCollimationWidth.getFloat64(value, pos);
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::getTableHeight(Float64& value, const unsigned long pos)
+{
+    return m_TableHeight.getFloat64(value, pos);
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::getTotalCollimationWidth(Float64& value,
+                                                                                         const unsigned long pos)
+{
+    return m_TotalCollimationWidth.getFloat64(value, pos);
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::read(DcmItem& item)
+{
+    clearData();
+
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_ReferencedPathIndex, "1-n", "1C", "CTAcquisitionDetailsMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_RotationDirection, "1", "1C", "CTAcquisitionDetailsMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_RevolutionTime, "1", "1C", "CTAcquisitionDetailsMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_SingleCollimationWidth, "1", "1C", "CTAcquisitionDetailsMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_TotalCollimationWidth, "1", "1C", "CTAcquisitionDetailsMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_TableHeight, "1", "1C", "CTAcquisitionDetailsMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_GantryDetectorTilt, "1", "1C", "CTAcquisitionDetailsMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_DataCollectionDiameter, "1", "1C", "CTAcquisitionDetailsMacro");
+
+    return EC_Normal;
+}
+
+FGCTAcquisitionDetails::E_RotationDirection
+FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::rotaDir2Enum(const OFString& str)
+{
+    if (str == "CC")
+        return E_RotationDirection_CC;
+    else if (str == "CW")
+        return E_RotationDirection_CW;
+    else if (str.empty())
+        return E_RotationDirection_Empty;
+    else
+        return E_RotationDirection_Invalid;
+}
+
+OFBool
+FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::rotaDir2Str(const FGCTAcquisitionDetails::E_RotationDirection& rota,
+                                                                OFString& result)
+{
+    switch (rota)
+    {
+        case FGCTAcquisitionDetails::E_RotationDirection_CC:
+            result = "CC";
+            break;
+        case FGCTAcquisitionDetails::E_RotationDirection_CW:
+            result = "CW";
+            break;
+        case FGCTAcquisitionDetails::E_RotationDirection_Empty:
+            result = "";
+            break;
+        case FGCTAcquisitionDetails::E_RotationDirection_Invalid:
+            result = "";
+            return OFFalse;
+        default:
+            result = "";
+            DCMFG_WARN("Unknown value for enum FGCTAcquisitionDetails::E_RotationDirection: " << rota);
+            return OFFalse;
+    }
+    return OFTrue;
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::setDataCollectionDiameter(const Float64 value,
+                                                                                          const OFBool checkValue)
+{
+    (void)checkValue;
+    return m_DataCollectionDiameter.putFloat64(value);
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::setGantryDetectorTilt(const Float64 value,
+                                                                                      const OFBool checkValue)
+{
+    (void)checkValue;
+    return m_GantryDetectorTilt.putFloat64(value);
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::setReferencedPathIndex(const OFVector<Uint16>& values,
+                                                                                       const OFBool checkValues)
+{
+    (void)checkValues;
+    return DcmIODUtil::setUint16ValuesOnElement(m_ReferencedPathIndex, values, "1-n", checkValues);
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::setRotationDirection(
+    const FGCTAcquisitionDetails::E_RotationDirection& value, const OFBool checkValue)
+{
+    (void)checkValue;
+    OFString val;
+    if (rotaDir2Str(value, val))
+    {
+        return m_RotationDirection.putOFStringArray(val);
+    }
+    else
+        return FG_EC_InvalidData;
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::setRevolutionTime(const Float64 value,
+                                                                                  const bool checkValue)
+{
+    (void)checkValue;
+    return m_RevolutionTime.putFloat64(value);
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::setSingleCollimationWidth(const Float64 value,
+                                                                                          const OFBool checkValue)
+{
+    (void)checkValue;
+    return m_SingleCollimationWidth.putFloat64(value);
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::setTableHeight(const Float64 value,
+                                                                               const OFBool checkValue)
+{
+    (void)checkValue;
+    return m_TableHeight.putFloat64(value);
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::setTotalCollimationWidth(const Float64 value,
+                                                                                         const OFBool checkValue)
+{
+    (void)checkValue;
+    return m_TotalCollimationWidth.putFloat64(value);
+}
+
+OFCondition FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::write(DcmItem& item)
+{
+    // --- write frame content macro attributes ---
+    OFCondition result;
+    DcmIODUtil::copyElementToDataset(result, item, m_ReferencedPathIndex, "1-n", "1C", "CTAcquisitionDetailsMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_RotationDirection, "1", "1C", "CTAcquisitionDetailsMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_RevolutionTime, "1", "1C", "CTAcquisitionDetailsMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_SingleCollimationWidth, "1", "1C", "CTAcquisitionDetailsMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_TotalCollimationWidth, "1", "1C", "CTAcquisitionDetailsMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_TableHeight, "1", "1C", "CTAcquisitionDetailsMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_GantryDetectorTilt, "1", "1C", "CTAcquisitionDetailsMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_DataCollectionDiameter, "1", "1C", "CTAcquisitionDetailsMacro");
+
+    return result;
+}
+
+FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem* FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem::clone() const
+{
+    FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem* copy = new FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem();
+    if (copy)
+    {
+        copy->m_ReferencedPathIndex    = this->m_ReferencedPathIndex;
+        copy->m_RotationDirection      = this->m_RotationDirection;
+        copy->m_RevolutionTime         = this->m_RevolutionTime;
+        copy->m_SingleCollimationWidth = this->m_SingleCollimationWidth;
+        copy->m_TotalCollimationWidth  = this->m_TotalCollimationWidth;
+        copy->m_TableHeight            = this->m_TableHeight;
+        copy->m_GantryDetectorTilt     = this->m_GantryDetectorTilt;
+        copy->m_DataCollectionDiameter = this->m_DataCollectionDiameter;
+    }
+    return copy;
+}
diff --git a/dcmfg/libsrc/fgctacquisitiontype.cc b/dcmfg/libsrc/fgctacquisitiontype.cc
new file mode 100644 (file)
index 0000000..d0b0e41
--- /dev/null
@@ -0,0 +1,303 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT Acquisition Type Functional Group
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgctacquisitiontype.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/dcmiod/iodutil.h"
+
+const OFString FGCTAcquisitionType::DT_AcquisitionType_Sequenced     = "SEQUENCED";
+const OFString FGCTAcquisitionType::DT_AcquisitionType_Spiral        = "SPIRAL";
+const OFString FGCTAcquisitionType::DT_AcquisitionType_ConstantAngle = "CONSTANT_ANGLE";
+const OFString FGCTAcquisitionType::DT_AcquisitionType_Stationary    = "STATIONARY";
+const OFString FGCTAcquisitionType::DT_AcquisitionType_Free          = "FREE";
+
+// Constructor
+FGCTAcquisitionType::FGCTAcquisitionType()
+    : FGBase(DcmFGTypes::EFG_CTACQUISITIONTYPE)
+    , m_AcquisitionType(DCM_AcquisitionType)
+    , m_TubeAngle(DCM_TubeAngle)
+    , m_ConstantVolumeFlag(DCM_ConstantVolumeFlag)
+    , m_FluoroscopyFlag(DCM_FluoroscopyFlag)
+{
+}
+
+FGCTAcquisitionType::~FGCTAcquisitionType()
+{
+    // nothing to do
+}
+
+FGBase* FGCTAcquisitionType::clone() const
+{
+    FGCTAcquisitionType* copy = new FGCTAcquisitionType();
+    if (copy)
+    {
+        copy->m_AcquisitionType    = this->m_AcquisitionType;
+        copy->m_TubeAngle          = this->m_TubeAngle;
+        copy->m_ConstantVolumeFlag = this->m_ConstantVolumeFlag;
+        copy->m_FluoroscopyFlag    = this->m_FluoroscopyFlag;
+    }
+    return copy;
+}
+
+void FGCTAcquisitionType::clearData()
+{
+    m_AcquisitionType.clear();
+    m_TubeAngle.clear();
+    m_ConstantVolumeFlag.clear();
+    m_FluoroscopyFlag.clear();
+}
+
+OFCondition FGCTAcquisitionType::check() const
+{
+    // Maybe add checks later
+    return EC_Normal;
+}
+
+/// Read CT Acquisition Type Sequence from given item
+OFCondition FGCTAcquisitionType::read(DcmItem& item)
+{
+    clearData();
+
+    DcmItem* seqItem   = NULL;
+    OFCondition result = getItemFromFGSequence(item, DCM_CTAcquisitionTypeSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_AcquisitionType, "1", "1", "CTAcquisitionTypeMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_TubeAngle, "1", "1", "CTAcquisitionTypeMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_ConstantVolumeFlag, "1", "1", "CTAcquisitionTypeMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FluoroscopyFlag, "1", "1", "CTAcquisitionTypeMacro");
+    return EC_Normal;
+}
+
+/// Writes single CT Acquisition Type Sequence into given item
+OFCondition FGCTAcquisitionType::write(DcmItem& item)
+{
+    DcmItem* seqItem   = NULL;
+    OFCondition result = createNewFGSequence(item, DCM_CTAcquisitionTypeSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+
+    // --- write frame content macro attributes ---
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_AcquisitionType, "1", "1", "CTAcquisitionTypeMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_TubeAngle, "1", "1", "CTAcquisitionTypeMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_ConstantVolumeFlag, "1", "1", "CTAcquisitionTypeMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_FluoroscopyFlag, "1", "1", "CTAcquisitionTypeMacro");
+    return result;
+}
+
+int FGCTAcquisitionType::compare(const FGBase& rhs) const
+{
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
+
+    const FGCTAcquisitionType* myRhs = OFstatic_cast(const FGCTAcquisitionType*, &rhs);
+    if (!myRhs)
+        return -1;
+
+    // Compare all elements
+    result = m_AcquisitionType.compare(myRhs->m_AcquisitionType);
+    if (result == 0)
+        result = m_TubeAngle.compare(myRhs->m_TubeAngle);
+    if (result == 0)
+        result = m_ConstantVolumeFlag.compare(myRhs->m_ConstantVolumeFlag);
+    if (result == 0)
+        result = m_FluoroscopyFlag.compare(myRhs->m_FluoroscopyFlag);
+
+    return result;
+}
+
+// --- get() functionality ---
+
+OFCondition FGCTAcquisitionType::getAcquisitionType(OFString& value, const signed long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_AcquisitionType, value, pos);
+}
+
+OFCondition FGCTAcquisitionType::getTubeAngle(Float64& value, const unsigned long pos)
+{
+    return m_TubeAngle.getFloat64(value, pos);
+}
+
+OFCondition FGCTAcquisitionType::getConstantVolumeFlag(FGCTAcquisitionType::E_ConstantVolumeFlag& value, const long pos)
+{
+    OFString str;
+    DcmIODUtil::getStringValueFromElement(m_ConstantVolumeFlag, str, pos);
+    value = constVolFlag2Enum(str);
+    if ((value != FGCTAcquisitionType::E_ConstVol_Empty) && (value != FGCTAcquisitionType::E_ConstVol_Invalid))
+        return EC_Normal;
+    else
+        return EC_InvalidValue;
+}
+
+OFCondition FGCTAcquisitionType::getConstantVolumeFlag(OFString& value, const signed long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_ConstantVolumeFlag, value, pos);
+}
+
+OFCondition FGCTAcquisitionType::getFluoroscopyFlag(FGCTAcquisitionType::E_FluoroscopyFlag& value, const long pos)
+{
+    OFString str;
+    DcmIODUtil::getStringValueFromElement(m_FluoroscopyFlag, str, pos);
+    value = fluoroscopyFlag2Enum(str);
+    if ((value != FGCTAcquisitionType::E_Fluoroscopy_Empty) && (value != FGCTAcquisitionType::E_Fluoroscopy_Invalid))
+        return EC_Normal;
+    else
+        return EC_InvalidValue;
+}
+
+OFCondition FGCTAcquisitionType::getFluoroscopyFlag(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_FluoroscopyFlag, value, pos);
+}
+
+// --- set() functionality ---
+
+OFCondition FGCTAcquisitionType::setAcquisitionType(const OFString& value, const OFBool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_AcquisitionType.putOFStringArray(value);
+    return result;
+}
+
+OFCondition FGCTAcquisitionType::setTubeAngle(const Float64& value, const OFBool checkValue)
+{
+    return m_TubeAngle.putFloat64(value);
+}
+
+OFCondition FGCTAcquisitionType::setConstantVolumeFlag(const FGCTAcquisitionType::E_ConstantVolumeFlag& value,
+                                                       const OFBool checkValue)
+{
+    (void)checkValue;
+    OFString val;
+    if (constVolFlag2Str(value, val))
+    {
+        return m_ConstantVolumeFlag.putOFStringArray(val);
+    }
+    else
+        return FG_EC_InvalidData;
+}
+
+OFCondition FGCTAcquisitionType::setConstantVolumeFlag(const OFString& value, const OFBool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_ConstantVolumeFlag.putOFStringArray(value);
+    return result;
+}
+
+OFCondition FGCTAcquisitionType::setFluoroscopyFlag(const FGCTAcquisitionType::E_FluoroscopyFlag& value,
+                                                    const OFBool checkValue)
+{
+    (void)checkValue;
+    OFString val;
+    if (fluoroscopyFlag2Str(value, val))
+    {
+        return m_FluoroscopyFlag.putOFStringArray(val);
+    }
+    else
+        return FG_EC_InvalidData;
+}
+
+OFCondition FGCTAcquisitionType::setFluoroscopyFlag(const OFString& value, const OFBool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_FluoroscopyFlag.putOFStringArray(value);
+    return result;
+}
+
+FGCTAcquisitionType::E_ConstantVolumeFlag FGCTAcquisitionType::constVolFlag2Enum(const OFString& str)
+{
+    if (str == "NO")
+        return E_ConstVol_No;
+    else if (str == "YES")
+        return E_ConstVol_Yes;
+    else if (str.empty())
+        return E_ConstVol_Empty;
+    else
+        return E_ConstVol_Invalid;
+}
+
+OFBool FGCTAcquisitionType::constVolFlag2Str(const FGCTAcquisitionType::E_ConstantVolumeFlag& eval, OFString& result)
+{
+    switch (eval)
+    {
+        case FGCTAcquisitionType::E_ConstVol_No:
+            result = "NO";
+            break;
+        case FGCTAcquisitionType::E_ConstVol_Yes:
+            result = "YES";
+            break;
+        case FGCTAcquisitionType::E_ConstVol_Empty:
+            result = "";
+            break;
+        case FGCTAcquisitionType::E_ConstVol_Invalid:
+            result = "";
+            return OFFalse;
+        default:
+            result = "";
+            DCMFG_WARN("Unknown value for enum FGCTAcquisitionType::E_ConstantVolumeFlag: " << eval);
+            return OFFalse;
+    }
+    return OFTrue;
+}
+
+FGCTAcquisitionType::E_FluoroscopyFlag FGCTAcquisitionType::fluoroscopyFlag2Enum(const OFString& str)
+{
+    if (str == "NO")
+        return E_Fluoroscopy_No;
+    else if (str == "YES")
+        return E_Fluoroscopy_Yes;
+    else if (str.empty())
+        return E_Fluoroscopy_Empty;
+    else
+        return E_Fluoroscopy_Invalid;
+}
+
+OFBool FGCTAcquisitionType::fluoroscopyFlag2Str(const FGCTAcquisitionType::E_FluoroscopyFlag& eval, OFString& result)
+{
+    switch (eval)
+    {
+        case FGCTAcquisitionType::E_Fluoroscopy_No:
+            result = "NO";
+            break;
+        case FGCTAcquisitionType::E_Fluoroscopy_Yes:
+            result = "YES";
+            break;
+        case FGCTAcquisitionType::E_Fluoroscopy_Empty:
+            result = "";
+            break;
+        case FGCTAcquisitionType::E_Fluoroscopy_Invalid:
+            result = "";
+            return OFFalse;
+        default:
+            result = "";
+            DCMFG_WARN("Unknown value for enum FGCTAcquisitionType::E_FluoroscopyFlag: " << eval);
+            return OFFalse;
+    }
+    return OFTrue;
+}
diff --git a/dcmfg/libsrc/fgctadditionalxraysource.cc b/dcmfg/libsrc/fgctadditionalxraysource.cc
new file mode 100644 (file)
index 0000000..b29ebd6
--- /dev/null
@@ -0,0 +1,362 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmfg
+ *
+ *  Author: Michael Onken
+ *
+ *  Purpose: Class for managing the CT Additional X-Ray Source
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgctadditionalxraysource.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/dcmiod/iodutil.h"
+
+FGCTAdditionalXRaySource::FGCTAdditionalXRaySource()
+    : FGBase(DcmFGTypes::EFG_CTADDITIONALXRAYSOURCE)
+    , m_Items()
+{
+}
+
+OFCondition FGCTAdditionalXRaySource::check() const
+{
+    // TODO Maybe add checks later
+    return EC_Normal;
+}
+
+void FGCTAdditionalXRaySource::clearData()
+{
+    DcmIODUtil::freeContainer(m_Items);
+    m_Items.clear();
+}
+
+int FGCTAdditionalXRaySource::compare(const FGBase& rhs) const
+{
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
+
+    FGCTAdditionalXRaySource* myRhs
+        = OFconst_cast(FGCTAdditionalXRaySource*, (OFstatic_cast(const FGCTAdditionalXRaySource*, &rhs)));
+    if (!myRhs)
+        return -1;
+
+    // Compare all items
+    return DcmIODUtil::compareContainer(m_Items, myRhs->getCTAdditionalXRaySourceItems());
+}
+
+OFCondition FGCTAdditionalXRaySource::read(DcmItem& item)
+{
+    clearData();
+    DcmItem* seqItem       = NULL;
+    unsigned long numItems = 0;
+    OFCondition result     = getNumItemsFromFGSequence(item, DCM_CTAdditionalXRaySourceSequence, numItems);
+    if (result.bad())
+        return result;
+
+    for (unsigned long num = 0; num < numItems; num++)
+    {
+        if (getItemFromFGSequence(item, DCM_CTAdditionalXRaySourceSequence, num, seqItem).good())
+        {
+            FGCTAdditionalXRaySourceItem* newItem = new FGCTAdditionalXRaySourceItem();
+            newItem->read(*seqItem);
+            m_Items.push_back(newItem);
+        }
+    }
+    return EC_Normal;
+}
+
+OFCondition FGCTAdditionalXRaySource::write(DcmItem& item)
+{
+    OFCondition result = check();
+    if (result.good())
+    {
+        DcmIODUtil::writeSubSequence(
+            result, DCM_CTAdditionalXRaySourceSequence, m_Items, item, "1-n", "2", "CT Additional X-Ray Source");
+    }
+
+    return result;
+}
+
+FGBase* FGCTAdditionalXRaySource::clone() const
+{
+    OFunique_ptr<FGCTAdditionalXRaySource> copy(new FGCTAdditionalXRaySource());
+    if (copy)
+    {
+        if (DcmIODUtil::copyContainer(this->m_Items, copy->m_Items).good())
+        {
+            return copy.release();
+        }
+    }
+    return OFnullptr;
+}
+
+OFVector<FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem*>&
+FGCTAdditionalXRaySource::getCTAdditionalXRaySourceItems()
+{
+    return m_Items;
+}
+
+FGCTAdditionalXRaySource::~FGCTAdditionalXRaySource()
+{
+    clearData();
+}
+
+FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::FGCTAdditionalXRaySourceItem()
+    : m_KVP(DCM_KVP)
+    , m_XRayTubeCurrentInmA(DCM_XRayTubeCurrentInmA)
+    , m_DataCollectionDiameter(DCM_DataCollectionDiameter)
+    , m_FocalSpots(DCM_FocalSpots)
+    , m_FilterType(DCM_FilterType)
+    , m_FilterMaterial(DCM_FilterMaterial)
+    , m_ExposureInmAs(DCM_ExposureInmAs)
+    , m_EnergyWeightingFactor(DCM_EnergyWeightingFactor)
+{
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::check() const
+{
+    // TODO: Maybe add checks lager
+    return EC_Normal;
+}
+
+FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::~FGCTAdditionalXRaySourceItem()
+{
+    // nothing to do
+}
+
+void FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::clearData()
+{
+    m_KVP.clear();
+    m_XRayTubeCurrentInmA.clear();
+    m_DataCollectionDiameter.clear();
+    m_FocalSpots.clear();
+    m_FilterType.clear();
+    m_FilterMaterial.clear();
+    m_ExposureInmAs.clear();
+    m_EnergyWeightingFactor.clear();
+}
+
+FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem*
+FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::clone() const
+{
+    if (FGCTAdditionalXRaySourceItem* copy = new FGCTAdditionalXRaySourceItem)
+    {
+        copy->m_KVP                    = m_KVP;
+        copy->m_XRayTubeCurrentInmA    = m_XRayTubeCurrentInmA;
+        copy->m_DataCollectionDiameter = m_DataCollectionDiameter;
+        copy->m_FocalSpots             = m_FocalSpots;
+        copy->m_FilterType             = m_FilterType;
+        copy->m_FilterMaterial         = m_FilterMaterial;
+        copy->m_ExposureInmAs          = m_ExposureInmAs;
+        copy->m_EnergyWeightingFactor  = m_EnergyWeightingFactor;
+        return copy;
+    }
+    return OFnullptr;
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::read(DcmItem& item)
+{
+    clearData();
+
+    OFCondition result;
+
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_KVP, "1", "1", "CT Additional X-Ray Source");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_XRayTubeCurrentInmA, "1", "1", "CT Additional X-Ray Source");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_DataCollectionDiameter, "1", "1", "CT Additional X-Ray Source");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_FocalSpots, "1-n", "1", "CT Additional X-Ray Source");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_FilterType, "1", "1", "CT Additional X-Ray Source");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_FilterMaterial, "1-n", "1", "CT Additional X-Ray Source");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_ExposureInmAs, "1", "1", "CT Additional X-Ray Source");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_EnergyWeightingFactor, "1", "1C", "CT Additional X-Ray Source");
+
+    return EC_Normal;
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::write(DcmItem& item)
+{
+    OFCondition result = check();
+    if (result.bad())
+        return result;
+
+    DcmIODUtil::copyElementToDataset(result, item, m_KVP, "1", "1", "CT Additional X-Ray Source");
+    DcmIODUtil::copyElementToDataset(result, item, m_XRayTubeCurrentInmA, "1", "1", "CT Additional X-Ray Source");
+    DcmIODUtil::copyElementToDataset(result, item, m_DataCollectionDiameter, "1", "1", "CT Additional X-Ray Source");
+    DcmIODUtil::copyElementToDataset(result, item, m_FocalSpots, "1-n", "1", "CT Additional X-Ray Source");
+    DcmIODUtil::copyElementToDataset(result, item, m_FilterType, "1", "1", "CT Additional X-Ray Source");
+    DcmIODUtil::copyElementToDataset(result, item, m_FilterMaterial, "1-n", "1", "CT Additional X-Ray Source");
+    DcmIODUtil::copyElementToDataset(result, item, m_ExposureInmAs, "1", "1", "CT Additional X-Ray Source");
+    DcmIODUtil::copyElementToDataset(result, item, m_EnergyWeightingFactor, "1", "1C", "CT Additional X-Ray Source");
+
+    return result;
+}
+
+int FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::compare(
+    const FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem& rhs) const
+{
+    int result                                = 0;
+    const FGCTAdditionalXRaySourceItem* myRhs = OFstatic_cast(const FGCTAdditionalXRaySourceItem*, &rhs);
+
+    // Compare all elements
+    result = m_KVP.compare(myRhs->m_KVP);
+    if (result == 0)
+        result = m_XRayTubeCurrentInmA.compare(myRhs->m_XRayTubeCurrentInmA);
+    if (result == 0)
+        result = m_DataCollectionDiameter.compare(myRhs->m_DataCollectionDiameter);
+    if (result == 0)
+        result = m_FocalSpots.compare(myRhs->m_FocalSpots);
+    if (result == 0)
+        result = m_FilterType.compare(myRhs->m_FilterType);
+    if (result == 0)
+        result = m_FilterMaterial.compare(myRhs->m_FilterMaterial);
+    if (result == 0)
+        result = m_ExposureInmAs.compare(myRhs->m_ExposureInmAs);
+    if (result == 0)
+        result = m_EnergyWeightingFactor.compare(myRhs->m_EnergyWeightingFactor);
+
+    return result;
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::getKVP(OFString& value, const signed long pos) const
+{
+    return DcmIODUtil::getStringValueFromElement(m_KVP, value, pos);
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::getXRayTubeCurrentInmA(Float64& value,
+                                                                                           const unsigned long pos) const
+{
+    return DcmIODUtil::getFloat64ValueFromElement(m_XRayTubeCurrentInmA, value, pos);
+}
+
+OFCondition
+FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::getDataCollectionDiameter(OFString& value,
+                                                                                  const signed long pos) const
+{
+    return DcmIODUtil::getStringValueFromElement(m_DataCollectionDiameter, value, pos);
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::getFocalSpots(OFString& value,
+                                                                                  const signed long pos) const
+{
+    return DcmIODUtil::getStringValueFromElement(m_FocalSpots, value, pos);
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::getFilterType(OFString& value,
+                                                                                  const signed long pos) const
+{
+    return DcmIODUtil::getStringValueFromElement(m_FilterType, value, pos);
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::getFilterMaterial(OFString& value,
+                                                                                      const signed long pos) const
+{
+    return DcmIODUtil::getStringValueFromElement(m_FilterMaterial, value, pos);
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::getExposureInmAs(Float64& value,
+                                                                                     const unsigned long pos) const
+{
+    return DcmIODUtil::getFloat64ValueFromElement(m_ExposureInmAs, value, pos);
+}
+
+OFCondition
+FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::getEnergyWeightingFactor(Float32& value,
+                                                                                 const unsigned long pos) const
+{
+    return DcmIODUtil::getFloat32ValueFromElement(m_EnergyWeightingFactor, value, pos);
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::setKVP(const OFString& value,
+                                                                           const OFBool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_KVP.putString(value.c_str());
+    return result;
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::setKVP(const Float64 value, const OFBool checkValue)
+{
+    (void)checkValue;
+    return m_KVP.putFloat64(value);
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::setXRayTubeCurrentInmA(const Float64 value,
+                                                                                           const OFBool checkValue)
+{
+    return m_XRayTubeCurrentInmA.putFloat64(value);
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::setDataCollectionDiameter(const OFString& value,
+                                                                                              const OFBool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_DataCollectionDiameter.putString(value.c_str());
+    return result;
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::setDataCollectionDiameter(const Float64 value,
+                                                                                              const OFBool checkValue)
+{
+    return m_DataCollectionDiameter.putFloat64(value);
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::setFocalSpots(const OFString& value,
+                                                                                  const OFBool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_FocalSpots.putString(value.c_str());
+    return result;
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::setFocalSpots(const OFVector<Float64>& values,
+                                                                                  const OFBool checkValue)
+{
+    return DcmIODUtil::setFloat64ValuesOnElement(m_FocalSpots, values, "1-n", checkValue);
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::setFilterType(const OFString& value,
+                                                                                  const OFBool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_FilterType.putString(value.c_str());
+    return result;
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::setFilterMaterial(const OFString& value,
+                                                                                      const OFBool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_FilterMaterial.putString(value.c_str());
+    return result;
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::setExposureInmAs(const Float64 value,
+                                                                                     const OFBool checkValue)
+{
+    return m_ExposureInmAs.putFloat64(value);
+}
+
+OFCondition FGCTAdditionalXRaySource::FGCTAdditionalXRaySourceItem::setEnergyWeightingFactor(const Float32 value,
+                                                                                             const OFBool checkValue)
+{
+    return m_EnergyWeightingFactor.putFloat32(value);
+}
diff --git a/dcmfg/libsrc/fgctexposure.cc b/dcmfg/libsrc/fgctexposure.cc
new file mode 100644 (file)
index 0000000..c56f92c
--- /dev/null
@@ -0,0 +1,459 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT Exposure Functional Group
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgctexposure.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/dcmiod/iodmacro.h"
+#include "dcmtk/dcmiod/iodutil.h"
+
+// Constructor
+FGCTExposure::FGCTExposureItem::FGCTExposureItem()
+    : m_ReferencedPathIndex(DCM_ReferencedPathIndex)
+    , m_ExposureTimeInMs(DCM_ExposureTimeInms)
+    , m_XRayTubeCurrentInMa(DCM_XRayTubeCurrentInmA)
+    , m_ExposureInMas(DCM_ExposureInmAs)
+    , m_ExposureModulationType(DCM_ExposureModulationType)
+    , m_EstimatedDoseSaving(DCM_EstimatedDoseSaving)
+    , m_CTDIVol(DCM_CTDIvol)
+    , m_CTDIPhantomTypeCodeSequence()
+    , m_WaterEquivalentDiameter(DCM_WaterEquivalentDiameter)
+    , m_WaterEquivalentDiameterCalculationMethodCodeSequence()
+    , m_ImageAndFluoroscopyAreaDoseProduct(DCM_ImageAndFluoroscopyAreaDoseProduct)
+{
+}
+
+FGCTExposure::FGCTExposureItem::FGCTExposureItem(const FGCTExposureItem& rhs)
+    : m_ReferencedPathIndex(rhs.m_ReferencedPathIndex)
+    , m_ExposureTimeInMs(rhs.m_ExposureTimeInMs)
+    , m_XRayTubeCurrentInMa(rhs.m_XRayTubeCurrentInMa)
+    , m_ExposureInMas(rhs.m_ExposureInMas)
+    , m_ExposureModulationType(rhs.m_ExposureModulationType)
+    , m_EstimatedDoseSaving(rhs.m_EstimatedDoseSaving)
+    , m_CTDIVol(rhs.m_CTDIVol)
+    , m_CTDIPhantomTypeCodeSequence()
+    , m_WaterEquivalentDiameter(rhs.m_WaterEquivalentDiameter)
+    , m_WaterEquivalentDiameterCalculationMethodCodeSequence()
+    , m_ImageAndFluoroscopyAreaDoseProduct(rhs.m_ImageAndFluoroscopyAreaDoseProduct)
+{
+    DcmIODUtil::copyContainer(rhs.m_CTDIPhantomTypeCodeSequence, this->m_CTDIPhantomTypeCodeSequence);
+    DcmIODUtil::copyContainer(rhs.m_WaterEquivalentDiameterCalculationMethodCodeSequence,
+                              this->m_WaterEquivalentDiameterCalculationMethodCodeSequence);
+}
+
+FGCTExposure::FGCTExposureItem::~FGCTExposureItem()
+{
+    DcmIODUtil::freeContainer(m_CTDIPhantomTypeCodeSequence);
+    DcmIODUtil::freeContainer(m_WaterEquivalentDiameterCalculationMethodCodeSequence);
+}
+
+FGCTExposure::FGCTExposureItem* FGCTExposure::FGCTExposureItem::clone() const
+{
+    OFCondition result;
+    OFunique_ptr<FGCTExposureItem> copy(new FGCTExposureItem);
+    if (copy)
+    {
+        copy->m_ReferencedPathIndex                = this->m_ReferencedPathIndex;
+        copy->m_ExposureTimeInMs                   = this->m_ExposureTimeInMs;
+        copy->m_XRayTubeCurrentInMa                = this->m_XRayTubeCurrentInMa;
+        copy->m_ExposureInMas                      = this->m_ExposureInMas;
+        copy->m_ExposureModulationType             = this->m_ExposureModulationType;
+        copy->m_EstimatedDoseSaving                = this->m_EstimatedDoseSaving;
+        copy->m_CTDIVol                            = this->m_CTDIVol;
+        copy->m_WaterEquivalentDiameter            = this->m_WaterEquivalentDiameter;
+        copy->m_ImageAndFluoroscopyAreaDoseProduct = this->m_ImageAndFluoroscopyAreaDoseProduct;
+        // Copy sequences
+        result = DcmIODUtil::copyContainer(this->m_CTDIPhantomTypeCodeSequence, copy->m_CTDIPhantomTypeCodeSequence);
+        if (result.good())
+            DcmIODUtil::copyContainer(this->m_WaterEquivalentDiameterCalculationMethodCodeSequence,
+                                      copy->m_WaterEquivalentDiameterCalculationMethodCodeSequence);
+        if (result.good())
+            return copy.release();
+    }
+    return OFnullptr;
+}
+
+void FGCTExposure::FGCTExposureItem::clearData()
+{
+    m_ReferencedPathIndex.clear();
+    m_ExposureTimeInMs.clear();
+    m_XRayTubeCurrentInMa.clear();
+    m_ExposureInMas.clear();
+    m_ExposureModulationType.clear();
+    m_EstimatedDoseSaving.clear();
+    m_CTDIVol.clear();
+    m_WaterEquivalentDiameter.clear();
+    m_ImageAndFluoroscopyAreaDoseProduct.clear();
+    // clear sequences
+    DcmIODUtil::freeContainer(m_CTDIPhantomTypeCodeSequence);
+    DcmIODUtil::freeContainer(m_WaterEquivalentDiameterCalculationMethodCodeSequence);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::check() const
+{
+    // Maybe add checks later
+    return EC_Normal;
+}
+
+/// Read CT Exposure Sequence from given item
+OFCondition FGCTExposure::FGCTExposureItem::read(DcmItem& item)
+{
+    clearData();
+
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_ReferencedPathIndex, "1-n", "1C", "CTExposureMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_ExposureTimeInMs, "1", "1C", "CTExposureMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_XRayTubeCurrentInMa, "1", "1C", "CTExposureMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_ExposureInMas, "1", "1C", "CTExposureMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_ExposureModulationType, "1-n", "1C", "CTExposureMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_EstimatedDoseSaving, "1", "2C", "CTExposureMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_CTDIVol, "1", "2C", "CTExposureMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_WaterEquivalentDiameter, "1", "3", "CTExposureMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_ImageAndFluoroscopyAreaDoseProduct, "1", "3", "CTExposureMacro");
+
+    DcmIODUtil::readSubSequence(
+        item, DCM_CTDIPhantomTypeCodeSequence, m_CTDIPhantomTypeCodeSequence, "1", "3", "CTExposureMacro");
+    DcmIODUtil::readSubSequence(item,
+                                DCM_WaterEquivalentDiameterCalculationMethodCodeSequence,
+                                m_WaterEquivalentDiameterCalculationMethodCodeSequence,
+                                "1",
+                                "3",
+                                "CTExposureMacro");
+
+    return EC_Normal;
+}
+
+/// Writes single CT Exposure Sequence into given item
+OFCondition FGCTExposure::FGCTExposureItem::write(DcmItem& item)
+{
+    OFCondition result;
+
+    // --- write frame content macro attributes ---
+    DcmIODUtil::copyElementToDataset(result, item, m_ReferencedPathIndex, "1-n", "1C", "CTExposureMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_ExposureTimeInMs, "1", "1C", "CTExposureMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_XRayTubeCurrentInMa, "1", "1C", "CTExposureMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_ExposureInMas, "1", "1C", "CTExposureMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_ExposureModulationType, "1-n", "1C", "CTExposureMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_EstimatedDoseSaving, "1", "2C", "CTExposureMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_CTDIVol, "1", "2C", "CTExposureMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_WaterEquivalentDiameter, "1", "3", "CTExposureMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_ImageAndFluoroscopyAreaDoseProduct, "1", "3", "CTExposureMacro");
+    DcmIODUtil::writeSubSequence(
+        result, DCM_CTDIPhantomTypeCodeSequence, m_CTDIPhantomTypeCodeSequence, item, "1", "3", "CTExposureMacro");
+    DcmIODUtil::writeSubSequence(result,
+                                 DCM_WaterEquivalentDiameterCalculationMethodCodeSequence,
+                                 m_WaterEquivalentDiameterCalculationMethodCodeSequence,
+                                 item,
+                                 "1",
+                                 "3",
+                                 "CTExposureMacro");
+
+    return result;
+}
+
+int FGCTExposure::FGCTExposureItem::compare(const FGCTExposure::FGCTExposureItem& rhs) const
+{
+    FGCTExposureItem* myRhs = OFconst_cast(FGCTExposureItem*, OFstatic_cast(const FGCTExposureItem*, &rhs));
+    if (!myRhs)
+        return -1;
+
+    // Compare all elements
+    int result = m_ReferencedPathIndex.compare(myRhs->m_ReferencedPathIndex);
+    if (result == 0)
+        result = m_ExposureTimeInMs.compare(myRhs->m_ExposureTimeInMs);
+    if (result == 0)
+        result = m_XRayTubeCurrentInMa.compare(myRhs->m_XRayTubeCurrentInMa);
+    if (result == 0)
+        result = m_ExposureInMas.compare(myRhs->m_ExposureInMas);
+    if (result == 0)
+        result = m_ExposureModulationType.compare(myRhs->m_ExposureModulationType);
+    if (result == 0)
+        result = m_EstimatedDoseSaving.compare(myRhs->m_EstimatedDoseSaving);
+    if (result == 0)
+        result = m_CTDIVol.compare(myRhs->m_CTDIVol);
+    if (result == 0)
+        result = m_WaterEquivalentDiameter.compare(myRhs->m_WaterEquivalentDiameter);
+    if (result == 0)
+        result = m_ImageAndFluoroscopyAreaDoseProduct.compare(myRhs->m_ImageAndFluoroscopyAreaDoseProduct);
+    if (result == 0)
+        result = DcmIODUtil::compareContainer(m_CTDIPhantomTypeCodeSequence, myRhs->m_CTDIPhantomTypeCodeSequence);
+    if (result == 0)
+        result = DcmIODUtil::compareContainer(m_WaterEquivalentDiameterCalculationMethodCodeSequence,
+                                              myRhs->m_WaterEquivalentDiameterCalculationMethodCodeSequence);
+
+    return result;
+}
+
+// --- get() functionality ---
+
+OFCondition FGCTExposure::FGCTExposureItem::getReferencedPathIndex(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_ReferencedPathIndex, value, pos);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::getExposureTimeInMs(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_ExposureTimeInMs, value, pos);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::getExposureTimeInMs(Float64& value, const unsigned long pos)
+{
+    return m_ExposureTimeInMs.getFloat64(value, pos);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::getXRayTubeCurrentInMa(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_XRayTubeCurrentInMa, value, pos);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::getXRayTubeCurrentInMa(Float64& value, const unsigned long pos)
+{
+    return m_XRayTubeCurrentInMa.getFloat64(value, pos);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::getExposureInMas(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_ExposureInMas, value, pos);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::getExposureInMas(Float64& value, const unsigned long pos)
+{
+    return m_ExposureInMas.getFloat64(value, pos);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::getExposureModulationType(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_ExposureModulationType, value, pos);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::getEstimatedDoseSaving(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_EstimatedDoseSaving, value, pos);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::getEstimatedDoseSaving(Float64& value, const unsigned long pos)
+{
+    return m_EstimatedDoseSaving.getFloat64(value, pos);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::getCTDIVol(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_CTDIVol, value, pos);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::getCTDIVol(Float64& value, const unsigned long pos)
+{
+    return m_CTDIVol.getFloat64(value, pos);
+}
+
+OFVector<CodeSequenceMacro*>& FGCTExposure::FGCTExposureItem::getCTDIPhantomTypeCodeSequence()
+{
+    return m_CTDIPhantomTypeCodeSequence;
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::getWaterEquivalentDiameter(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_WaterEquivalentDiameter, value, pos);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::getWaterEquivalentDiameter(Float64& value, const unsigned long pos)
+{
+    return m_WaterEquivalentDiameter.getFloat64(value, pos);
+}
+
+OFVector<CodeSequenceMacro*>& FGCTExposure::FGCTExposureItem::getWaterEquivalentDiameterCalculationMethodCodeSequence()
+{
+    return m_WaterEquivalentDiameterCalculationMethodCodeSequence;
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::getImageAndFluoroscopyAreaDoseProduct(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_ImageAndFluoroscopyAreaDoseProduct, value, pos);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::getImageAndFluoroscopyAreaDoseProduct(Float64& value,
+                                                                                  const unsigned long pos)
+{
+    return m_ImageAndFluoroscopyAreaDoseProduct.getFloat64(value, pos);
+}
+
+// --- set() functionality ---
+
+OFCondition FGCTExposure::FGCTExposureItem::setReferencedPathIndex(const OFVector<Uint16>& values,
+                                                                   const bool checkValues)
+{
+    (void)checkValues;
+    return DcmIODUtil::setUint16ValuesOnElement(m_ReferencedPathIndex, values, "1-n", checkValues);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::setExposureTimeInMs(const Float64 value, const bool checkValue)
+{
+    (void)checkValue;
+    return m_ExposureTimeInMs.putFloat64(value);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::setXRayTubeCurrentInMa(const Float64 value, const bool checkValue)
+{
+    (void)checkValue;
+    return m_XRayTubeCurrentInMa.putFloat64(value);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::setExposureInMas(const Float64 value, const bool checkValue)
+{
+    (void)checkValue;
+    return m_ExposureInMas.putFloat64(value);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::setExposureModulationType(const OFString& value, const bool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1-n") : EC_Normal;
+    if (result.good())
+        result = m_ExposureModulationType.putString(value.c_str());
+    return result;
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::setEstimatedDoseSaving(const Float64 value, const bool checkValue)
+{
+    (void)checkValue;
+    return m_EstimatedDoseSaving.putFloat64(value);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::setCTDIVol(const Float64 value, const bool checkValue)
+{
+    (void)checkValue;
+    return m_CTDIVol.putFloat64(value);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::setWaterEquivalentDiameter(const Float64 value, const bool checkValue)
+{
+    (void)checkValue;
+    return m_WaterEquivalentDiameter.putFloat64(value);
+}
+
+OFCondition FGCTExposure::FGCTExposureItem::setImageAndFluoroscopyAreaDoseProduct(const Float64 value,
+                                                                                  const bool checkValue)
+{
+    (void)checkValue;
+    return m_ImageAndFluoroscopyAreaDoseProduct.putFloat64(value);
+}
+
+// ---------------------
+
+// Constructor
+FGCTExposure::FGCTExposure()
+    : FGBase(DcmFGTypes::EFG_CTEXPOSURE)
+    , m_Items()
+{
+}
+
+FGCTExposure::FGCTExposure(const FGCTExposure& rhs)
+    : FGBase(rhs)
+    , m_Items()
+{
+    OFCondition result = DcmIODUtil::copyContainer(rhs.m_Items, this->m_Items);
+    if (result.bad())
+    {
+        DCMFG_ERROR("Cannot copy FGCTExposure class: " << result.text());
+    }
+}
+
+FGCTExposure::~FGCTExposure()
+{
+    DcmIODUtil::freeContainer(m_Items);
+}
+
+FGBase* FGCTExposure::clone() const
+{
+    OFunique_ptr<FGCTExposure> copy(new FGCTExposure());
+    if (copy)
+    {
+        if (DcmIODUtil::copyContainer(this->m_Items, copy->m_Items).good())
+        {
+            return copy.release();
+        }
+    }
+    return OFnullptr;
+}
+
+void FGCTExposure::clearData()
+{
+    DcmIODUtil::freeContainer(m_Items);
+    m_Items.clear();
+}
+
+OFCondition FGCTExposure::check() const
+{
+    // Maybe add checks later
+    return EC_Normal;
+}
+
+/// Read CT Exposure Sequence from given item
+OFCondition FGCTExposure::read(DcmItem& item)
+{
+    clearData();
+    DcmItem* seqItem       = NULL;
+    unsigned long numItems = 0;
+    OFCondition result     = getNumItemsFromFGSequence(item, DCM_CTExposureSequence, numItems);
+    if (result.bad())
+        return result;
+
+    for (unsigned long num = 0; num < numItems; num++)
+    {
+        if (getItemFromFGSequence(item, DCM_CTExposureSequence, num, seqItem).good())
+        {
+            FGCTExposureItem* newItem = new FGCTExposureItem();
+            newItem->read(*seqItem);
+            m_Items.push_back(newItem);
+        }
+    }
+    return EC_Normal;
+}
+
+/// Writes single CT Exposure Sequence into given item
+OFCondition FGCTExposure::write(DcmItem& item)
+{
+    OFCondition result = check();
+    if (result.good())
+    {
+        DcmIODUtil::writeSubSequence(result, DCM_CTExposureSequence, m_Items, item, "1-n", "2", "CTGeometryMacro");
+    }
+    return result;
+}
+
+int FGCTExposure::compare(const FGBase& rhs) const
+{
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
+
+    const FGCTExposure* myRhs = OFstatic_cast(const FGCTExposure*, &rhs);
+    if (!myRhs)
+        return -1;
+
+    // Compare all items
+    return DcmIODUtil::compareContainer(this->m_Items, myRhs->m_Items);
+}
+
+OFVector<FGCTExposure::FGCTExposureItem*>& FGCTExposure::getCTExposureItems()
+{
+    return m_Items;
+}
diff --git a/dcmfg/libsrc/fgctgeometry.cc b/dcmfg/libsrc/fgctgeometry.cc
new file mode 100644 (file)
index 0000000..28de418
--- /dev/null
@@ -0,0 +1,250 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT Geometry Functional Group
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgctgeometry.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/dcmiod/iodutil.h"
+
+// Constructor
+FGCTGeometry::FGCTGeometryItem::FGCTGeometryItem()
+    : m_ReferencedPathIndex(DCM_ReferencedPathIndex)
+    , m_DistanceSourceToDetector(DCM_DistanceSourceToDetector)
+    , m_DistanceSourceToDataCollectionCenter(DCM_DistanceSourceToDataCollectionCenter)
+{
+}
+
+FGCTGeometry::FGCTGeometryItem::~FGCTGeometryItem()
+{
+    // nothing to do
+}
+
+FGCTGeometry::FGCTGeometryItem* FGCTGeometry::FGCTGeometryItem::clone() const
+{
+    FGCTGeometryItem* copy = new FGCTGeometryItem();
+    if (copy)
+    {
+        copy->m_ReferencedPathIndex                  = this->m_ReferencedPathIndex;
+        copy->m_DistanceSourceToDetector             = this->m_DistanceSourceToDetector;
+        copy->m_DistanceSourceToDataCollectionCenter = this->m_DistanceSourceToDataCollectionCenter;
+    }
+    return copy;
+}
+
+void FGCTGeometry::FGCTGeometryItem::clearData()
+{
+    m_ReferencedPathIndex.clear();
+    m_DistanceSourceToDetector.clear();
+    m_DistanceSourceToDataCollectionCenter.clear();
+}
+
+OFCondition FGCTGeometry::FGCTGeometryItem::check() const
+{
+    // Maybe add checks later
+    return EC_Normal;
+}
+
+/// Read CT Geometry Sequence from given item
+OFCondition FGCTGeometry::FGCTGeometryItem::read(DcmItem& item)
+{
+    clearData();
+
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_ReferencedPathIndex, "1-n", "1C", "CTGeometryMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_DistanceSourceToDetector, "1", "1C", "CTGeometryMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(
+        item, m_DistanceSourceToDataCollectionCenter, "1", "1C", "CTGeometryMacro");
+    return EC_Normal;
+}
+
+/// Writes single CT Geometry Sequence into given item
+OFCondition FGCTGeometry::FGCTGeometryItem::write(DcmItem& item)
+{
+    OFCondition result;
+
+    // --- write frame content macro attributes ---
+    DcmIODUtil::copyElementToDataset(result, item, m_ReferencedPathIndex, "1-n", "1C", "CTGeometryMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_DistanceSourceToDetector, "1", "1C", "CTGeometryMacro");
+    DcmIODUtil::copyElementToDataset(
+        result, item, m_DistanceSourceToDataCollectionCenter, "1", "1C", "CTGeometryMacro");
+    return result;
+}
+
+int FGCTGeometry::FGCTGeometryItem::compare(const FGCTGeometry::FGCTGeometryItem& rhs) const
+{
+    const FGCTGeometry::FGCTGeometryItem* myRhs = OFstatic_cast(const FGCTGeometry::FGCTGeometryItem*, &rhs);
+    if (!myRhs)
+        return -1;
+
+    // Compare all elements
+    int result = m_ReferencedPathIndex.compare(myRhs->m_ReferencedPathIndex);
+    if (result == 0)
+        result = m_DistanceSourceToDetector.compare(myRhs->m_DistanceSourceToDetector);
+    if (result == 0)
+        result = m_DistanceSourceToDataCollectionCenter.compare(myRhs->m_DistanceSourceToDataCollectionCenter);
+
+    return result;
+}
+
+// --- get() functionality ---
+
+OFCondition FGCTGeometry::FGCTGeometryItem::getReferencedPathIndex(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_ReferencedPathIndex, value, pos);
+}
+
+OFCondition FGCTGeometry::FGCTGeometryItem::getReferencedPathIndex(OFVector<Uint16>& values)
+{
+    return DcmIODUtil::getUint16ValuesFromElement(m_ReferencedPathIndex, values);
+}
+
+OFCondition FGCTGeometry::FGCTGeometryItem::getDistanceSourceToDataCollectionCenter(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_DistanceSourceToDataCollectionCenter, value, pos);
+}
+
+OFCondition FGCTGeometry::FGCTGeometryItem::getDistanceSourceToDataCollectionCenter(OFVector<Float64>& values)
+{
+    return DcmIODUtil::getFloat64ValuesFromElement(m_DistanceSourceToDataCollectionCenter, values);
+}
+
+OFCondition FGCTGeometry::FGCTGeometryItem::getDistanceSourceToDetector(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_DistanceSourceToDetector, value, pos);
+}
+
+OFCondition FGCTGeometry::FGCTGeometryItem::getDistanceSourceToDetector(Float64& value, const unsigned long pos)
+{
+    return m_DistanceSourceToDetector.getFloat64(value, pos);
+}
+
+// --- set() functionality ---
+
+OFCondition FGCTGeometry::FGCTGeometryItem::setReferencedPathIndex(const OFVector<Uint16>& values,
+                                                                   const bool checkValue)
+{
+    return DcmIODUtil::setUint16ValuesOnElement(m_ReferencedPathIndex, values, "1-n", checkValue);
+}
+
+OFCondition FGCTGeometry::FGCTGeometryItem::setDistanceSourceToDetector(const Float64 value, const bool checkValue)
+{
+    (void)checkValue;
+    return m_DistanceSourceToDetector.putFloat64(value, 0);
+}
+
+OFCondition FGCTGeometry::FGCTGeometryItem::setDistanceSourceToDataCollectionCenter(const Float64 value,
+                                                                                    const bool checkValue)
+{
+    (void)checkValue;
+    return m_DistanceSourceToDataCollectionCenter.putFloat64(value, 0);
+}
+
+// ------------------------
+
+// Constructor
+FGCTGeometry::FGCTGeometry()
+    : FGBase(DcmFGTypes::EFG_CTGEOMETRY)
+    , m_Items()
+{
+}
+
+FGCTGeometry::~FGCTGeometry()
+{
+    clearData();
+}
+
+FGBase* FGCTGeometry::clone() const
+{
+    OFunique_ptr<FGCTGeometry> copy(new FGCTGeometry);
+    if (copy)
+    {
+        if (DcmIODUtil::copyContainer(this->m_Items, copy->m_Items).good())
+        {
+            return copy.release();
+        }
+    }
+    return OFnullptr;
+}
+
+void FGCTGeometry::clearData()
+{
+    DcmIODUtil::freeContainer(m_Items);
+    m_Items.clear();
+}
+
+OFCondition FGCTGeometry::check() const
+{
+    // Maybe add checks later
+    return EC_Normal;
+}
+
+/// Read CT Geometry Sequence from given item
+OFCondition FGCTGeometry::read(DcmItem& item)
+{
+    clearData();
+    DcmItem* seqItem       = NULL;
+    unsigned long numItems = 0;
+    OFCondition result     = getNumItemsFromFGSequence(item, DCM_CTGeometrySequence, numItems);
+    if (result.bad())
+        return result;
+
+    for (unsigned long num = 0; num < numItems; num++)
+    {
+        if (getItemFromFGSequence(item, DCM_CTGeometrySequence, num, seqItem).good())
+        {
+            FGCTGeometryItem* newItem = new FGCTGeometryItem();
+            newItem->read(*seqItem);
+            m_Items.push_back(newItem);
+        }
+    }
+    return EC_Normal;
+}
+
+/// Writes single CT Geometry Sequence into given item
+OFCondition FGCTGeometry::write(DcmItem& item)
+{
+    OFCondition result = check();
+    if (result.good())
+    {
+        DcmIODUtil::writeSubSequence(result, DCM_CTGeometrySequence, m_Items, item, "1-n", "2", "CTGeometryMacro");
+    }
+    return result;
+}
+
+int FGCTGeometry::compare(const FGBase& rhs) const
+{
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
+
+    const FGCTGeometry* myRhs = OFstatic_cast(const FGCTGeometry*, &rhs);
+    if (!myRhs)
+        return -1;
+
+    // Compare all items
+    return DcmIODUtil::compareContainer(this->m_Items, myRhs->m_Items);
+}
+
+OFVector<FGCTGeometry::FGCTGeometryItem*>& FGCTGeometry::getCTGeometryItems()
+{
+    return m_Items;
+}
diff --git a/dcmfg/libsrc/fgctimageframetype.cc b/dcmfg/libsrc/fgctimageframetype.cc
new file mode 100644 (file)
index 0000000..3e52adf
--- /dev/null
@@ -0,0 +1,335 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT Image Frame Type Functional Group
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgctimageframetype.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/dcmiod/iodutil.h"
+
+const OFString FGCTImageFrameType::DT_VolBasedCalcTechnique_MaxIp         = "MAX_IP";
+const OFString FGCTImageFrameType::DT_VolBasedCalcTechnique_MinIp         = "MIN_IP";
+const OFString FGCTImageFrameType::DT_VolBasedCalcTechnique_VolumeRender  = "VOLUME_RENDER";
+const OFString FGCTImageFrameType::DT_VolBasedCalcTechnique_SurfaceRender = "SURFACE_RENDER";
+const OFString FGCTImageFrameType::DT_VolBasedCalcTechnique_Mpr           = "MPR";
+const OFString FGCTImageFrameType::DT_VolBasedCalcTechnique_CurvedMpr     = "CURVED_MPR";
+const OFString FGCTImageFrameType::DT_VolBasedCalcTechnique_None          = "NONE";
+const OFString FGCTImageFrameType::DT_VolBasedCalcTechnique_Mixed         = "MIXED";
+
+// Constructor
+FGCTImageFrameType::FGCTImageFrameType()
+    : FGBase(DcmFGTypes::EFG_CTIMAGEFRAMETYPE)
+    , m_FrameType(DCM_FrameType)
+    , m_PixelPresentation(DCM_PixelPresentation)
+    , m_VolumetricProperties(DCM_VolumetricProperties)
+    , m_VolumeBasedCalculationTechnique(DCM_VolumeBasedCalculationTechnique)
+{
+}
+
+FGCTImageFrameType::~FGCTImageFrameType()
+{
+    // nothing to do
+}
+
+FGBase* FGCTImageFrameType::clone() const
+{
+    FGCTImageFrameType* copy = new FGCTImageFrameType();
+    if (copy)
+    {
+        copy->m_FrameType                       = this->m_FrameType;
+        copy->m_PixelPresentation               = this->m_PixelPresentation;
+        copy->m_VolumetricProperties            = this->m_VolumetricProperties;
+        copy->m_VolumeBasedCalculationTechnique = this->m_VolumeBasedCalculationTechnique;
+    }
+    return copy;
+}
+
+void FGCTImageFrameType::clearData()
+{
+    m_FrameType.clear();
+    m_PixelPresentation.clear();
+    m_VolumetricProperties.clear();
+    m_VolumeBasedCalculationTechnique.clear();
+}
+
+OFCondition FGCTImageFrameType::check() const
+{
+    // Maybe add checks later
+    return EC_Normal;
+}
+
+/// Read CT Image Frame Type Sequence from given item
+OFCondition FGCTImageFrameType::read(DcmItem& item)
+{
+    clearData();
+
+    DcmItem* seqItem   = NULL;
+    OFCondition result = getItemFromFGSequence(item, DCM_CTImageFrameTypeSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FrameType, "4", "1", "CTImageFrameTypeMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_PixelPresentation, "1", "1", "CTImageFrameTypeMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_VolumetricProperties, "1", "1", "CTImageFrameTypeMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(
+        *seqItem, m_VolumeBasedCalculationTechnique, "1", "1", "CTImageFrameTypeMacro");
+    return EC_Normal;
+}
+
+/// Writes single CT Image Frame Type Sequence into given item
+OFCondition FGCTImageFrameType::write(DcmItem& item)
+{
+    DcmItem* seqItem   = NULL;
+    OFCondition result = createNewFGSequence(item, DCM_CTImageFrameTypeSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+
+    // --- write frame content macro attributes ---
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_FrameType, "4", "1", "CTImageFrameTypeMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_PixelPresentation, "1", "1", "CTImageFrameTypeMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_VolumetricProperties, "1", "1", "CTImageFrameTypeMacro");
+    DcmIODUtil::copyElementToDataset(
+        result, *seqItem, m_VolumeBasedCalculationTechnique, "1", "1", "CTImageFrameTypeMacro");
+    return result;
+}
+
+int FGCTImageFrameType::compare(const FGBase& rhs) const
+{
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
+
+    const FGCTImageFrameType* myRhs = OFstatic_cast(const FGCTImageFrameType*, &rhs);
+    if (!myRhs)
+        return -1;
+
+    // Compare all elements
+    result = m_FrameType.compare(myRhs->m_FrameType);
+    if (result == 0)
+        result = m_PixelPresentation.compare(myRhs->m_PixelPresentation);
+    if (result == 0)
+        result = m_VolumetricProperties.compare(myRhs->m_VolumetricProperties);
+    if (result == 0)
+        result = m_VolumeBasedCalculationTechnique.compare(myRhs->m_VolumeBasedCalculationTechnique);
+
+    return result;
+}
+
+// --- get() functionality ---
+
+OFCondition FGCTImageFrameType::getFrameType(OFString& value, const signed long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_FrameType, value, pos);
+}
+
+OFCondition FGCTImageFrameType::getPixelPresentation(OFString& value, const signed long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_PixelPresentation, value, pos);
+}
+
+OFCondition FGCTImageFrameType::getPixelPresentation(FGCTImageFrameType::E_PixelPresentation& value, const long pos)
+{
+    OFString str;
+    DcmIODUtil::getStringValueFromElement(m_PixelPresentation, str, pos);
+    value = pixelPres2Enum(str);
+    if ((value != FGCTImageFrameType::E_PixelPres_Empty) && (value != FGCTImageFrameType::E_PixelPres_Invalid))
+        return EC_Normal;
+    else
+        return EC_InvalidValue;
+}
+
+OFCondition FGCTImageFrameType::getVolumetricProperties(OFString& value, const signed long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_VolumetricProperties, value, pos);
+}
+
+OFCondition FGCTImageFrameType::getVolumetricProperties(FGCTImageFrameType::E_VolumetricProperties& value,
+                                                        const long pos)
+{
+    OFString str;
+    DcmIODUtil::getStringValueFromElement(m_VolumetricProperties, str, pos);
+    value = volProps2Enum(str);
+    if ((value != FGCTImageFrameType::E_VolProp_Empty) && (value != FGCTImageFrameType::E_VolProp_Invalid))
+        return EC_Normal;
+    else
+        return EC_InvalidValue;
+}
+
+OFCondition FGCTImageFrameType::getVolumeBasedCalculationTechnique(OFString& value, const signed long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_VolumeBasedCalculationTechnique, value, pos);
+}
+
+// --- set() functionality ---
+
+OFCondition FGCTImageFrameType::setFrameType(const OFString& value, const OFBool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "4") : EC_Normal;
+    if (result.good())
+        result = m_FrameType.putOFStringArray(value);
+    return result;
+}
+
+OFCondition FGCTImageFrameType::setPixelPresentation(const OFString& value, const OFBool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_PixelPresentation.putOFStringArray(value);
+    return result;
+}
+
+OFCondition FGCTImageFrameType::setPixelPresentation(const FGCTImageFrameType::E_PixelPresentation& value,
+                                                     const OFBool checkValue)
+{
+    (void)checkValue;
+    OFString val;
+    if (pixelPres2Str(value, val))
+    {
+        return m_PixelPresentation.putOFStringArray(val);
+    }
+    else
+        return FG_EC_InvalidData;
+}
+
+OFCondition FGCTImageFrameType::setVolumetricProperties(const OFString& value, const OFBool checkValue)
+{
+
+    if (checkValue)
+    {
+        if (!volProps2Enum(value))
+            return FG_EC_InvalidData;
+    }
+    return m_VolumetricProperties.putOFStringArray(value);
+}
+
+OFCondition FGCTImageFrameType::setVolumetricProperties(const FGCTImageFrameType::E_VolumetricProperties& value,
+                                                        const OFBool checkValue)
+{
+    (void)checkValue;
+    OFString val;
+    if (volProps2Str(value, val))
+    {
+        return m_VolumetricProperties.putOFStringArray(val);
+    }
+    else
+        return FG_EC_InvalidData;
+}
+
+OFCondition FGCTImageFrameType::setVolumeBasedCalculationTechnique(const OFString& value, const OFBool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_VolumeBasedCalculationTechnique.putOFStringArray(value);
+    return result;
+}
+
+FGCTImageFrameType::E_PixelPresentation FGCTImageFrameType::pixelPres2Enum(const OFString& str)
+{
+    if (str == "COLOR")
+        return E_PixelPres_Color;
+    else if (str == "MONOCHROME")
+        return E_PixelPres_Monochrome;
+    else if (str == "MIXED")
+        return E_PixelPres_Mixed;
+    else if (str == "TRUE_COLOR")
+        return E_PixelPres_TrueColor;
+    else if (str.empty())
+        return E_PixelPres_Empty;
+    else
+        return E_PixelPres_Invalid;
+}
+
+OFBool FGCTImageFrameType::pixelPres2Str(const FGCTImageFrameType::E_PixelPresentation& eval, OFString& result)
+{
+    switch (eval)
+    {
+        case E_PixelPres_Color:
+            result = "COLOR";
+            break;
+        case E_PixelPres_Monochrome:
+            result = "MONOCHROME";
+            break;
+        case E_PixelPres_Mixed:
+            result = "MIXED";
+            break;
+        case E_PixelPres_TrueColor:
+            result = "TRUE COLOR";
+            break;
+        case E_PixelPres_Empty:
+            result = "";
+            break;
+        case E_PixelPres_Invalid:
+            result = "";
+            return OFFalse;
+        default:
+            result = "";
+            DCMFG_WARN("Unknown value for enum FGCTImageFrameType::E_PixelPresentation: " << eval);
+            return OFFalse;
+    }
+    return OFTrue;
+}
+
+FGCTImageFrameType::E_VolumetricProperties FGCTImageFrameType::volProps2Enum(const OFString& str)
+{
+    if (str == "DISTORTED")
+        return E_VolProp_Distorted;
+    else if (str == "MIXED")
+        return E_VolProp_Mixed;
+    else if (str == "SAMPLED")
+        return E_VolProp_Sampled;
+    else if (str == "VOLUME")
+        return E_VolProp_Volume;
+    else if (str.empty())
+        return E_VolProp_Empty;
+    else
+        return E_VolProp_Invalid;
+}
+
+OFBool FGCTImageFrameType::volProps2Str(const FGCTImageFrameType::E_VolumetricProperties& eval, OFString& result)
+{
+    switch (eval)
+    {
+        case E_VolProp_Distorted:
+            result = "DISTORTED";
+            break;
+        case E_VolProp_Mixed:
+            result = "MIXED";
+            break;
+        case E_VolProp_Sampled:
+            result = "SAMPLED";
+            break;
+        case E_VolProp_Volume:
+            result = "VOLUME";
+            break;
+        case E_VolProp_Empty:
+            result = "";
+            break;
+        case E_VolProp_Invalid:
+            result = "";
+            return OFFalse;
+        default:
+            result = "";
+            DCMFG_WARN("Unknown value for enum FGCTImageFrameType::E_VolumetricProperties: " << eval);
+            return OFFalse;
+    }
+    return OFTrue;
+}
diff --git a/dcmfg/libsrc/fgctposition.cc b/dcmfg/libsrc/fgctposition.cc
new file mode 100644 (file)
index 0000000..c038d6c
--- /dev/null
@@ -0,0 +1,168 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT Position Functional Group
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgctposition.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/dcmiod/iodutil.h"
+
+// Constructor
+FGCTPosition::FGCTPosition()
+    : FGBase(DcmFGTypes::EFG_CTPOSITION)
+    , m_TablePosition(DCM_TablePosition)
+    , m_DataCollectionCenterPatient(DCM_DataCollectionCenterPatient)
+    , m_ReconstructionTargetCenterPatient(DCM_ReconstructionTargetCenterPatient)
+{
+}
+
+FGCTPosition::~FGCTPosition()
+{
+    // nothing to do
+}
+
+FGBase* FGCTPosition::clone() const
+{
+    FGCTPosition* copy = new FGCTPosition();
+    if (copy)
+    {
+        copy->m_TablePosition                     = this->m_TablePosition;
+        copy->m_DataCollectionCenterPatient       = this->m_DataCollectionCenterPatient;
+        copy->m_ReconstructionTargetCenterPatient = this->m_ReconstructionTargetCenterPatient;
+    }
+    return copy;
+}
+
+void FGCTPosition::clearData()
+{
+    m_TablePosition.clear();
+    m_DataCollectionCenterPatient.clear();
+    m_ReconstructionTargetCenterPatient.clear();
+}
+
+OFCondition FGCTPosition::check() const
+{
+    // Maybe add checks later
+    return EC_Normal;
+}
+
+/// Read CT Position Sequence from given item
+OFCondition FGCTPosition::read(DcmItem& item)
+{
+    clearData();
+
+    DcmItem* seqItem   = NULL;
+    OFCondition result = getItemFromFGSequence(item, DCM_CTPositionSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_TablePosition, "1", "1C", "CTPositionMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_DataCollectionCenterPatient, "3", "1C", "CTPositionMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(
+        *seqItem, m_ReconstructionTargetCenterPatient, "3", "1C", "CTPositionMacro");
+    return EC_Normal;
+}
+
+/// Writes single CT Position Sequence into given item
+OFCondition FGCTPosition::write(DcmItem& item)
+{
+    DcmItem* seqItem   = NULL;
+    OFCondition result = createNewFGSequence(item, DCM_CTPositionSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+
+    // --- write frame content macro attributes ---
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_TablePosition, "1", "1C", "CTPositionMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_DataCollectionCenterPatient, "3", "1C", "CTPositionMacro");
+    DcmIODUtil::copyElementToDataset(
+        result, *seqItem, m_ReconstructionTargetCenterPatient, "3", "1C", "CTPositionMacro");
+    return result;
+}
+
+int FGCTPosition::compare(const FGBase& rhs) const
+{
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
+
+    const FGCTPosition* myRhs = OFstatic_cast(const FGCTPosition*, &rhs);
+    if (!myRhs)
+        return -1;
+
+    // Compare all elements
+    result = m_TablePosition.compare(myRhs->m_TablePosition);
+    if (result == 0)
+        result = m_DataCollectionCenterPatient.compare(myRhs->m_DataCollectionCenterPatient);
+    if (result == 0)
+        result = m_ReconstructionTargetCenterPatient.compare(myRhs->m_ReconstructionTargetCenterPatient);
+
+    return result;
+}
+
+// --- get() functionality ---
+
+OFCondition FGCTPosition::getTablePosition(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_TablePosition, value, pos);
+}
+
+OFCondition FGCTPosition::getTablePosition(Float64& value, const unsigned long pos)
+{
+    return m_TablePosition.getFloat64(value, pos);
+}
+
+OFCondition FGCTPosition::getDataCollectionCenterPatient(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_DataCollectionCenterPatient, value, pos);
+}
+
+OFCondition FGCTPosition::getDataCollectionCenterPatient(OFVector<Float64>& values)
+{
+    return DcmIODUtil::getFloat64ValuesFromElement(m_DataCollectionCenterPatient, values);
+}
+
+OFCondition FGCTPosition::getReconstructionTargetCenterPatient(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_ReconstructionTargetCenterPatient, value, pos);
+}
+
+OFCondition FGCTPosition::getReconstructionTargetCenterPatient(OFVector<Float64>& values)
+{
+    return DcmIODUtil::getFloat64ValuesFromElement(m_ReconstructionTargetCenterPatient, values);
+}
+
+// --- set() functionality ---
+
+OFCondition FGCTPosition::setTablePosition(const Float64 value, const OFBool checkValue)
+{
+    return m_TablePosition.putFloat64(value);
+}
+
+OFCondition FGCTPosition::setDataCollectionCenterPatient(const OFVector<Float64>& values, const OFBool checkValue)
+{
+    return DcmIODUtil::setFloat64ValuesOnElement(m_DataCollectionCenterPatient, values, "3", checkValue);
+}
+
+OFCondition FGCTPosition::setReconstructionTargetCenterPatient(const OFVector<Float64>& values, const OFBool checkValue)
+{
+    return DcmIODUtil::setFloat64ValuesOnElement(m_ReconstructionTargetCenterPatient, values, "3", checkValue);
+}
diff --git a/dcmfg/libsrc/fgctreconstruction.cc b/dcmfg/libsrc/fgctreconstruction.cc
new file mode 100644 (file)
index 0000000..fd292f4
--- /dev/null
@@ -0,0 +1,285 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT Reconstruction Functional Group
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgctreconstruction.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/dcmiod/iodutil.h"
+
+// Constructor
+FGCTReconstruction::FGCTReconstruction()
+    : FGBase(DcmFGTypes::EFG_CTRECONSTRUCTION)
+    , m_ReconstructionAlgorithm(DCM_ReconstructionAlgorithm)
+    , m_ConvolutionKernel(DCM_ConvolutionKernel)
+    , m_ConvolutionKernelGroup(DCM_ConvolutionKernelGroup)
+    , m_ReconstructionDiameter(DCM_ReconstructionDiameter)
+    , m_ReconstructionFieldOfView(DCM_ReconstructionFieldOfView)
+    , m_ReconstructionPixelSpacing(DCM_ReconstructionPixelSpacing)
+    , m_ReconstructionAngle(DCM_ReconstructionAngle)
+    , m_ImageFilter(DCM_ImageFilter)
+{
+}
+
+FGCTReconstruction::~FGCTReconstruction()
+{
+    // nothing to do
+}
+
+FGBase* FGCTReconstruction::clone() const
+{
+    FGCTReconstruction* copy = new FGCTReconstruction();
+    if (copy)
+    {
+        copy->m_ReconstructionAlgorithm    = this->m_ReconstructionAlgorithm;
+        copy->m_ConvolutionKernel          = this->m_ConvolutionKernel;
+        copy->m_ConvolutionKernelGroup     = this->m_ConvolutionKernelGroup;
+        copy->m_ReconstructionDiameter     = this->m_ReconstructionDiameter;
+        copy->m_ReconstructionFieldOfView  = this->m_ReconstructionFieldOfView;
+        copy->m_ReconstructionPixelSpacing = this->m_ReconstructionPixelSpacing;
+        copy->m_ReconstructionAngle        = this->m_ReconstructionAngle;
+        copy->m_ImageFilter                = this->m_ImageFilter;
+    }
+    return copy;
+}
+
+void FGCTReconstruction::clearData()
+{
+    m_ReconstructionAlgorithm.clear();
+    m_ConvolutionKernel.clear();
+    m_ConvolutionKernelGroup.clear();
+    m_ReconstructionDiameter.clear();
+    m_ReconstructionFieldOfView.clear();
+    m_ReconstructionPixelSpacing.clear();
+    m_ReconstructionAngle.clear();
+    m_ImageFilter.clear();
+}
+
+OFCondition FGCTReconstruction::check() const
+{
+    // Maybe add checks later
+    return EC_Normal;
+}
+
+/// Read CT Reconstruction Sequence from given item
+OFCondition FGCTReconstruction::read(DcmItem& item)
+{
+    clearData();
+
+    DcmItem* seqItem   = NULL;
+    OFCondition result = getItemFromFGSequence(item, DCM_CTReconstructionSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_ReconstructionAlgorithm, "1", "1C", "CTReconstructionMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_ConvolutionKernel, "1-n", "1C", "CTReconstructionMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_ConvolutionKernelGroup, "1", "1C", "CTReconstructionMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_ReconstructionDiameter, "1", "1C", "CTReconstructionMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(
+        *seqItem, m_ReconstructionFieldOfView, "2", "1C", "CTReconstructionMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(
+        *seqItem, m_ReconstructionPixelSpacing, "2", "1C", "CTReconstructionMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_ReconstructionAngle, "1", "1C", "CTReconstructionMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_ImageFilter, "1", "1C", "CTReconstructionMacro");
+
+    return EC_Normal;
+}
+
+/// Writes single CT Reconstruction Sequence into given item
+OFCondition FGCTReconstruction::write(DcmItem& item)
+{
+    DcmItem* seqItem   = NULL;
+    OFCondition result = createNewFGSequence(item, DCM_CTReconstructionSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+
+    // --- write frame content macro attributes ---
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_ReconstructionAlgorithm, "1", "1C", "CTReconstructionMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_ConvolutionKernel, "1-n", "1C", "CTReconstructionMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_ConvolutionKernelGroup, "1", "1C", "CTReconstructionMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_ReconstructionDiameter, "1", "1C", "CTReconstructionMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_ReconstructionFieldOfView, "2", "1C", "CTReconstructionMacro");
+    DcmIODUtil::copyElementToDataset(
+        result, *seqItem, m_ReconstructionPixelSpacing, "2", "1C", "CTReconstructionMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_ReconstructionAngle, "1", "1C", "CTReconstructionMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_ImageFilter, "1", "1C", "CTReconstructionMacro");
+
+    return result;
+}
+
+int FGCTReconstruction::compare(const FGBase& rhs) const
+{
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
+
+    const FGCTReconstruction* myRhs = OFstatic_cast(const FGCTReconstruction*, &rhs);
+    if (!myRhs)
+        return -1;
+
+    // Compare all elements
+    result = m_ReconstructionAlgorithm.compare(myRhs->m_ReconstructionAlgorithm);
+    if (result == 0)
+        result = m_ConvolutionKernel.compare(myRhs->m_ConvolutionKernel);
+    if (result == 0)
+        result = m_ConvolutionKernelGroup.compare(myRhs->m_ConvolutionKernelGroup);
+    if (result == 0)
+        result = m_ReconstructionDiameter.compare(myRhs->m_ReconstructionDiameter);
+    if (result == 0)
+        result = m_ReconstructionFieldOfView.compare(myRhs->m_ReconstructionFieldOfView);
+    if (result == 0)
+        result = m_ReconstructionPixelSpacing.compare(myRhs->m_ReconstructionPixelSpacing);
+    if (result == 0)
+        result = m_ReconstructionAngle.compare(myRhs->m_ReconstructionAngle);
+    if (result == 0)
+        result = m_ImageFilter.compare(myRhs->m_ImageFilter);
+
+    return result;
+}
+
+// --- get() functionality ---
+
+OFCondition FGCTReconstruction::getReconstructionAlgorithm(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_ReconstructionAlgorithm, value, pos);
+}
+
+OFCondition FGCTReconstruction::getConvolutionKernel(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_ConvolutionKernel, value, pos);
+}
+
+OFCondition FGCTReconstruction::getConvolutionKernelGroup(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_ConvolutionKernelGroup, value, pos);
+}
+
+OFCondition FGCTReconstruction::getReconstructionDiameter(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_ReconstructionDiameter, value, pos);
+}
+
+OFCondition FGCTReconstruction::getReconstructionDiameter(Float64& value, const unsigned long pos)
+{
+    return m_ReconstructionDiameter.getFloat64(value, pos);
+}
+
+OFCondition FGCTReconstruction::getReconstructionFieldOfView(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_ReconstructionFieldOfView, value, pos);
+}
+
+OFCondition FGCTReconstruction::getReconstructionFieldOfView(OFVector<Float64>& values)
+{
+    return DcmIODUtil::getFloat64ValuesFromElement(m_ReconstructionFieldOfView, values);
+}
+
+OFCondition FGCTReconstruction::getReconstructionPixelSpacing(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_ReconstructionPixelSpacing, value, pos);
+}
+
+OFCondition FGCTReconstruction::getReconstructionPixelSpacing(OFVector<Float64>& values)
+{
+    return DcmIODUtil::getFloat64ValuesFromElement(m_ReconstructionPixelSpacing, values);
+}
+
+OFCondition FGCTReconstruction::getReconstructionAngle(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_ReconstructionAngle, value, pos);
+}
+
+OFCondition FGCTReconstruction::getReconstructionAngle(Float64& value, const unsigned long pos)
+{
+    return m_ReconstructionAngle.getFloat64(value, pos);
+}
+
+OFCondition FGCTReconstruction::getImageFilter(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_ImageFilter, value, pos);
+}
+
+// --- set() functionality ---
+
+OFCondition FGCTReconstruction::setReconstructionAlgorithm(const OFString& value, const bool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_ReconstructionAlgorithm.putString(value.c_str());
+    return result;
+}
+
+OFCondition FGCTReconstruction::setConvolutionKernel(const OFString& value, const bool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1-n") : EC_Normal;
+    if (result.good())
+        result = m_ConvolutionKernel.putString(value.c_str());
+    return result;
+}
+
+OFCondition FGCTReconstruction::setConvolutionKernelGroup(const OFString& value, const bool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_ConvolutionKernelGroup.putString(value.c_str());
+    return result;
+}
+
+OFCondition FGCTReconstruction::setReconstructionDiameter(const Float64 value, const bool checkValue)
+{
+    (void)checkValue;
+    return m_ReconstructionDiameter.putFloat64(value);
+}
+
+OFCondition
+FGCTReconstruction::setReconstructionFieldOfView(const Float64 value1, const Float64 value2, const bool checkValue)
+{
+    (void)checkValue;
+    OFCondition result = m_ReconstructionFieldOfView.putFloat64(value1, 0);
+    if (result.good())
+        result = m_ReconstructionFieldOfView.putFloat64(value2, 1);
+    return result;
+}
+
+OFCondition
+FGCTReconstruction::setReconstructionPixelSpacing(const Float64 value1, const Float64 value2, const bool checkValue)
+{
+    (void)checkValue;
+    OFCondition result = m_ReconstructionPixelSpacing.putFloat64(value1, 0);
+    if (result.good())
+        result = m_ReconstructionPixelSpacing.putFloat64(value2, 1);
+    return result;
+}
+
+OFCondition FGCTReconstruction::setReconstructionAngle(const Float64 value, const bool checkValue)
+{
+    (void)checkValue;
+    return m_ReconstructionAngle.putFloat64(value);
+}
+
+OFCondition FGCTReconstruction::setImageFilter(const OFString& value, const bool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_ImageFilter.putString(value.c_str());
+    return result;
+}
diff --git a/dcmfg/libsrc/fgcttabledynamics.cc b/dcmfg/libsrc/fgcttabledynamics.cc
new file mode 100644 (file)
index 0000000..c0e17dc
--- /dev/null
@@ -0,0 +1,247 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT Table Dynamics Functional Group
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgcttabledynamics.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/dcmiod/iodutil.h"
+
+// Constructor
+FGCTTableDynamics::FGCTTableDynamics()
+    : FGBase(DcmFGTypes::EFG_CTTABLEDYNAMICS)
+    , m_Items()
+{
+}
+
+FGCTTableDynamics::~FGCTTableDynamics()
+{
+    clearData();
+}
+
+FGBase* FGCTTableDynamics::clone() const
+{
+    OFunique_ptr<FGCTTableDynamics> copy(new FGCTTableDynamics);
+    if (copy)
+    {
+        if (DcmIODUtil::copyContainer(this->m_Items, copy->m_Items).good())
+        {
+            return copy.release();
+        }
+    }
+    return OFnullptr;
+}
+
+void FGCTTableDynamics::clearData()
+{
+    DcmIODUtil::freeContainer(m_Items);
+    m_Items.clear();
+}
+
+OFCondition FGCTTableDynamics::check() const
+{
+    // Maybe add checks later
+    return EC_Normal;
+}
+
+/// Read CT Table Dynamics Sequence from given item
+OFCondition FGCTTableDynamics::read(DcmItem& item)
+{
+    clearData();
+    DcmItem* seqItem       = NULL;
+    unsigned long numItems = 0;
+    OFCondition result     = getNumItemsFromFGSequence(item, DCM_CTTableDynamicsSequence, numItems);
+    if (result.bad())
+        return result;
+
+    for (unsigned long num = 0; num < numItems; num++)
+    {
+        if (getItemFromFGSequence(item, DCM_CTTableDynamicsSequence, num, seqItem).good())
+        {
+            FGCTTableDynamicsItem* newItem = new FGCTTableDynamicsItem();
+            newItem->read(*seqItem);
+            m_Items.push_back(newItem);
+        }
+    }
+    return EC_Normal;
+}
+
+/// Writes single CT Table Dynamics Sequence into given item
+OFCondition FGCTTableDynamics::write(DcmItem& item)
+{
+    OFCondition result = check();
+    if (result.good())
+    {
+        DcmIODUtil::writeSubSequence(
+            result, DCM_CTTableDynamicsSequence, m_Items, item, "1-n", "2", "CTTableDynamicsMacro");
+    }
+    return result;
+}
+
+int FGCTTableDynamics::compare(const FGBase& rhs) const
+{
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
+
+    const FGCTTableDynamics* myRhs = OFstatic_cast(const FGCTTableDynamics*, &rhs);
+    if (!myRhs)
+        return -1;
+
+    // Compare all items
+    return DcmIODUtil::compareContainer(this->m_Items, myRhs->m_Items);
+}
+
+OFVector<FGCTTableDynamics::FGCTTableDynamicsItem*>& FGCTTableDynamics::getCTTableDynamicsItems()
+{
+    return m_Items;
+}
+
+// --------------------------------------------------------------------------
+
+// Constructor
+FGCTTableDynamics::FGCTTableDynamicsItem::FGCTTableDynamicsItem()
+    : m_TableSpeed(DCM_TableSpeed)
+    , m_TableFeedPerRotation(DCM_TableFeedPerRotation)
+    , m_SpiralPitchFactor(DCM_SpiralPitchFactor)
+{
+}
+
+FGCTTableDynamics::FGCTTableDynamicsItem::~FGCTTableDynamicsItem()
+{
+    // nothing to do
+}
+
+FGCTTableDynamics::FGCTTableDynamicsItem* FGCTTableDynamics::FGCTTableDynamicsItem::clone() const
+{
+    FGCTTableDynamicsItem* copy = new FGCTTableDynamicsItem();
+    if (copy)
+    {
+        copy->m_TableSpeed           = this->m_TableSpeed;
+        copy->m_TableFeedPerRotation = this->m_TableFeedPerRotation;
+        copy->m_SpiralPitchFactor    = this->m_SpiralPitchFactor;
+    }
+    return copy;
+}
+
+void FGCTTableDynamics::FGCTTableDynamicsItem::clearData()
+{
+    m_TableSpeed.clear();
+    m_TableFeedPerRotation.clear();
+    m_SpiralPitchFactor.clear();
+}
+
+OFCondition FGCTTableDynamics::FGCTTableDynamicsItem::check() const
+{
+    // Maybe add checks later
+    return EC_Normal;
+}
+
+/// Read CT Table Dynamics Sequence from given item
+OFCondition FGCTTableDynamics::FGCTTableDynamicsItem::read(DcmItem& item)
+{
+    clearData();
+
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_TableSpeed, "1", "1C", "CTTableDynamicsMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_TableFeedPerRotation, "1", "1C", "CTTableDynamicsMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_SpiralPitchFactor, "1", "1C", "CTTableDynamicsMacro");
+    return EC_Normal;
+}
+
+/// Writes single CT Table Dynamics Sequence into given item
+OFCondition FGCTTableDynamics::FGCTTableDynamicsItem::write(DcmItem& item)
+{
+    // --- write frame content macro attributes ---
+    OFCondition result;
+    DcmIODUtil::copyElementToDataset(result, item, m_TableSpeed, "1", "1C", "CTTableDynamicsMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_TableFeedPerRotation, "1", "1C", "CTTableDynamicsMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_SpiralPitchFactor, "1", "1C", "CTTableDynamicsMacro");
+    return result;
+}
+
+int FGCTTableDynamics::FGCTTableDynamicsItem::compare(const FGCTTableDynamics::FGCTTableDynamicsItem& rhs) const
+{
+    int result                         = 0;
+    const FGCTTableDynamicsItem* myRhs = OFstatic_cast(const FGCTTableDynamicsItem*, &rhs);
+    if (!myRhs)
+        return -1;
+
+    // Compare all elements
+    result = m_TableSpeed.compare(myRhs->m_TableSpeed);
+    if (result == 0)
+        result = m_TableFeedPerRotation.compare(myRhs->m_TableFeedPerRotation);
+    if (result == 0)
+        result = m_SpiralPitchFactor.compare(myRhs->m_SpiralPitchFactor);
+
+    return result;
+}
+
+// --- get() functionality ---
+
+OFCondition FGCTTableDynamics::FGCTTableDynamicsItem::getTableSpeed(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_TableSpeed, value, pos);
+}
+
+OFCondition FGCTTableDynamics::FGCTTableDynamicsItem::getTableSpeed(Float64& value, const unsigned long pos)
+{
+    return m_TableSpeed.getFloat64(value, pos);
+}
+
+OFCondition FGCTTableDynamics::FGCTTableDynamicsItem::getSpiralPitchFactor(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_SpiralPitchFactor, value, pos);
+}
+
+OFCondition FGCTTableDynamics::FGCTTableDynamicsItem::getSpiralPitchFactor(Float64& value, const unsigned long pos)
+{
+    return m_SpiralPitchFactor.getFloat64(value, pos);
+}
+
+OFCondition FGCTTableDynamics::FGCTTableDynamicsItem::getTableFeedPerRotation(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_TableFeedPerRotation, value, pos);
+}
+
+OFCondition FGCTTableDynamics::FGCTTableDynamicsItem::getTableFeedPerRotation(Float64& value, const unsigned long pos)
+{
+    return m_TableFeedPerRotation.getFloat64(value, pos);
+}
+
+// --- set() functionality ---
+
+OFCondition FGCTTableDynamics::FGCTTableDynamicsItem::setTableSpeed(const Float64& value, const OFBool checkValue)
+{
+    return m_TableSpeed.putFloat64(value);
+}
+
+OFCondition FGCTTableDynamics::FGCTTableDynamicsItem::setTableFeedPerRotation(const Float64& value,
+                                                                              const OFBool checkValue)
+{
+    return m_TableFeedPerRotation.putFloat64(value);
+}
+
+OFCondition FGCTTableDynamics::FGCTTableDynamicsItem::setSpiralPitchFactor(const Float64& value,
+                                                                           const OFBool checkValue)
+{
+    return m_SpiralPitchFactor.putFloat64(value);
+}
diff --git a/dcmfg/libsrc/fgctxraydetails.cc b/dcmfg/libsrc/fgctxraydetails.cc
new file mode 100644 (file)
index 0000000..85fd49d
--- /dev/null
@@ -0,0 +1,359 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the CT X-Ray Details Functional Group
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgctxraydetails.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/dcmiod/iodmacro.h"
+#include "dcmtk/dcmiod/iodutil.h"
+
+// Constructor
+FGCTXRayDetails::FGCTXRayDetails()
+    : FGBase(DcmFGTypes::EFG_CTXRAYDETAILS)
+    , m_Items()
+{
+}
+
+FGCTXRayDetails::~FGCTXRayDetails()
+{
+    DcmIODUtil::freeContainer(m_Items);
+}
+
+FGBase* FGCTXRayDetails::clone() const
+{
+    OFunique_ptr<FGCTXRayDetails> copy(new FGCTXRayDetails);
+    if (copy)
+    {
+        if (DcmIODUtil::copyContainer(this->m_Items, copy->m_Items).good())
+        {
+            return copy.release();
+        }
+    }
+    return OFnullptr;
+}
+
+void FGCTXRayDetails::clearData()
+{
+    DcmIODUtil::freeContainer(m_Items);
+    m_Items.clear();
+}
+
+OFCondition FGCTXRayDetails::check() const
+{
+    // Maybe add checks later
+    return EC_Normal;
+}
+
+/// Read CT X-Ray Details Sequence from given item
+OFCondition FGCTXRayDetails::read(DcmItem& item)
+{
+    clearData();
+    DcmItem* seqItem       = NULL;
+    unsigned long numItems = 0;
+    OFCondition result     = getNumItemsFromFGSequence(item, DCM_CTXRayDetailsSequence, numItems);
+    if (result.bad())
+        return result;
+
+    for (unsigned long num = 0; num < numItems; num++)
+    {
+        if (getItemFromFGSequence(item, DCM_CTXRayDetailsSequence, num, seqItem).good())
+        {
+            FGCTXRayDetailsItem* newItem = new FGCTXRayDetailsItem();
+            newItem->read(*seqItem);
+            m_Items.push_back(newItem);
+        }
+    }
+    return EC_Normal;
+}
+
+/// Writes single CT X-Ray Details Sequence into given item
+OFCondition FGCTXRayDetails::write(DcmItem& item)
+{
+    OFCondition result = check();
+    if (result.good())
+    {
+        DcmIODUtil::writeSubSequence(
+            result, DCM_CTXRayDetailsSequence, m_Items, item, "1-n", "2", "CTXRayDetailsMacro");
+    }
+    return result;
+}
+
+int FGCTXRayDetails::compare(const FGBase& rhs) const
+{
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
+
+    const FGCTXRayDetails* myRhs = OFstatic_cast(const FGCTXRayDetails*, &rhs);
+    if (!myRhs)
+        return -1;
+
+    // Compare all items
+    return DcmIODUtil::compareContainer(this->m_Items, myRhs->m_Items);
+}
+
+OFVector<FGCTXRayDetails::FGCTXRayDetailsItem*>& FGCTXRayDetails::getCTXRayDetailsItems()
+{
+    return m_Items;
+}
+
+// ---------------------------------------------
+
+// Constructor
+FGCTXRayDetails::FGCTXRayDetailsItem::FGCTXRayDetailsItem()
+    : m_ReferencedPathIndex(DCM_ReferencedPathIndex)
+    , m_KVP(DCM_KVP)
+    , m_FocalSpots(DCM_FocalSpots)
+    , m_FilterType(DCM_FilterType)
+    , m_FilterMaterial(DCM_FilterMaterial)
+    , m_CalciumScoringMassFactorPatient(DCM_CalciumScoringMassFactorPatient)
+    , m_CalciumScoringMassFactorDevice(DCM_CalciumScoringMassFactorDevice)
+    , m_EnergyWeightingFactor(DCM_EnergyWeightingFactor)
+{
+}
+
+FGCTXRayDetails::FGCTXRayDetailsItem::~FGCTXRayDetailsItem()
+{
+    // nothing to do
+}
+
+FGCTXRayDetails::FGCTXRayDetailsItem* FGCTXRayDetails::FGCTXRayDetailsItem::clone() const
+{
+    FGCTXRayDetailsItem* copy = new FGCTXRayDetailsItem();
+    if (copy)
+    {
+        copy->m_ReferencedPathIndex             = this->m_ReferencedPathIndex;
+        copy->m_KVP                             = this->m_KVP;
+        copy->m_FocalSpots                      = this->m_FocalSpots;
+        copy->m_FilterType                      = this->m_FilterType;
+        copy->m_FilterMaterial                  = this->m_FilterMaterial;
+        copy->m_CalciumScoringMassFactorPatient = this->m_CalciumScoringMassFactorPatient;
+        copy->m_CalciumScoringMassFactorDevice  = this->m_CalciumScoringMassFactorDevice;
+        copy->m_EnergyWeightingFactor           = this->m_EnergyWeightingFactor;
+    }
+    return copy;
+}
+
+void FGCTXRayDetails::FGCTXRayDetailsItem::clearData()
+{
+    m_ReferencedPathIndex.clear();
+    m_KVP.clear();
+    m_FocalSpots.clear();
+    m_FilterType.clear();
+    m_FilterMaterial.clear();
+    m_CalciumScoringMassFactorPatient.clear();
+    m_CalciumScoringMassFactorDevice.clear();
+    m_EnergyWeightingFactor.clear();
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::check() const
+{
+    // Maybe add checks later
+    return EC_Normal;
+}
+
+/// Read CT X-Ray Details Sequence from given item
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::read(DcmItem& item)
+{
+    clearData();
+
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_ReferencedPathIndex, "1-n", "1C", "CTXRayDetailsMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_KVP, "1", "1C", "CTXRayDetailsMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_FocalSpots, "1-n", "1C", "CTXRayDetailsMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_FilterType, "1", "1C", "CTXRayDetailsMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_FilterMaterial, "1-n", "1C", "CTXRayDetailsMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_CalciumScoringMassFactorPatient, "1", "3", "CTXRayDetailsMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_CalciumScoringMassFactorDevice, "3", "3", "CTXRayDetailsMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_EnergyWeightingFactor, "1", "3", "CTXRayDetailsMacro");
+    return EC_Normal;
+}
+
+/// Writes single CT X-Ray Details Sequence into given item
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::write(DcmItem& item)
+{
+    // --- write frame content macro attributes ---
+    OFCondition result;
+    DcmIODUtil::copyElementToDataset(result, item, m_ReferencedPathIndex, "1-n", "1C", "CTXRayDetailsMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_KVP, "1", "1C", "CTXRayDetailsMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_FocalSpots, "1-n", "1C", "CTXRayDetailsMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_FilterType, "1", "1C", "CTXRayDetailsMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_FilterMaterial, "1-n", "1C", "CTXRayDetailsMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_CalciumScoringMassFactorPatient, "1", "3", "CTXRayDetailsMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_CalciumScoringMassFactorDevice, "3", "3", "CTXRayDetailsMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_EnergyWeightingFactor, "1", "3", "CTXRayDetailsMacro");
+
+    return result;
+}
+
+int FGCTXRayDetails::FGCTXRayDetailsItem::compare(const FGCTXRayDetails::FGCTXRayDetailsItem& rhs) const
+{
+    const FGCTXRayDetails::FGCTXRayDetailsItem* myRhs
+        = OFstatic_cast(const FGCTXRayDetails::FGCTXRayDetailsItem*, &rhs);
+    if (!myRhs)
+        return -1;
+
+    // Compare all elements
+    int result = m_ReferencedPathIndex.compare(myRhs->m_ReferencedPathIndex);
+    if (result == 0)
+        result = m_KVP.compare(myRhs->m_KVP);
+    if (result == 0)
+        result = m_FocalSpots.compare(myRhs->m_FocalSpots);
+    if (result == 0)
+        result = m_FilterType.compare(myRhs->m_FilterType);
+    if (result == 0)
+        result = m_FilterMaterial.compare(myRhs->m_FilterMaterial);
+    if (result == 0)
+        result = m_CalciumScoringMassFactorPatient.compare(myRhs->m_CalciumScoringMassFactorPatient);
+    if (result == 0)
+        result = m_CalciumScoringMassFactorDevice.compare(myRhs->m_CalciumScoringMassFactorDevice);
+    if (result == 0)
+        result = m_EnergyWeightingFactor.compare(myRhs->m_EnergyWeightingFactor);
+
+    return result;
+}
+
+// --- get() functionality ---
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::getReferencedPathIndex(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_ReferencedPathIndex, value, pos);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::getReferencedPathIndex(OFVector<Uint16>& values)
+{
+    return DcmIODUtil::getUint16ValuesFromElement(m_ReferencedPathIndex, values);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::getKVP(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_KVP, value, pos);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::getKVP(Float64& value, const unsigned long pos)
+{
+    return m_KVP.getFloat64(value, pos);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::getFocalSpots(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_FocalSpots, value, pos);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::getFocalSpots(OFVector<Float64>& values)
+{
+    return DcmIODUtil::getFloat64ValuesFromElement(m_FocalSpots, values);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::getFilterType(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_FilterType, value, pos);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::getFilterMaterial(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_FilterType, value, pos);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::getCalciumScoringMassFactorPatient(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_CalciumScoringMassFactorPatient, value, pos);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::getCalciumScoringMassFactorPatient(Float32& value,
+                                                                                     const unsigned long pos)
+{
+    return m_CalciumScoringMassFactorPatient.getFloat32(value, pos);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::getCalciumScoringMassFactorDevice(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_CalciumScoringMassFactorDevice, value, pos);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::getCalciumScoringMassFactorDevice(OFVector<Float64>& values)
+{
+    return DcmIODUtil::getFloat64ValuesFromElement(m_CalciumScoringMassFactorDevice, values);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::getEnergyWeightingFactor(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_EnergyWeightingFactor, value, pos);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::getEnergyWeightingFactor(Float32& value, const unsigned long pos)
+{
+    return m_EnergyWeightingFactor.getFloat32(value, pos);
+}
+
+// --- set() functionality ---
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::setReferencedPathIndex(const OFVector<Uint16>& values,
+                                                                         const bool checkValues)
+{
+    (void)checkValues;
+    return DcmIODUtil::setUint16ValuesOnElement(m_ReferencedPathIndex, values, "1-n", checkValues);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::setKVP(const Float64 value, const bool checkValue)
+{
+    (void)checkValue;
+    return m_KVP.putFloat64(value);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::setFocalSpots(const OFVector<Float64>& values, const bool checkValues)
+{
+    return DcmIODUtil::setFloat64ValuesOnElement(m_FocalSpots, values, "1-n", checkValues);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::setFilterType(const OFString& value, const bool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_FilterType.putString(value.c_str());
+    return result;
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::setFilterMaterial(const OFString& value, const bool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1-n") : EC_Normal;
+    if (result.good())
+        result = m_FilterMaterial.putString(value.c_str());
+    return result;
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::setCalciumScoringMassFactorPatient(const Float32 value,
+                                                                                     const bool checkValue)
+{
+    return m_CalciumScoringMassFactorPatient.putFloat32(value);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::setCalciumScoringMassFactorDevice(const OFVector<Float32>& values,
+                                                                                    const bool checkValues)
+{
+    return DcmIODUtil::setFloat32ValuesOnElement(m_CalciumScoringMassFactorDevice, values, "1-n", checkValues);
+}
+
+OFCondition FGCTXRayDetails::FGCTXRayDetailsItem::setEnergyWeightingFactor(const Float32 value, const bool checkValue)
+{
+    return m_EnergyWeightingFactor.putFloat32(value);
+}
index d6874474508e67171987ff0bbc29e99e440c2d1a..f36e9c960cc0beaa1072a93259f24d1fe9ab2af4 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016-2018, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmdata/dcitem.h"
+
 #include "dcmtk/dcmdata/dcdatutl.h"
+#include "dcmtk/dcmdata/dcitem.h"
 #include "dcmtk/dcmfg/fgderimg.h"
 #include "dcmtk/dcmiod/iodutil.h"
 
-
-FGDerivationImage::FGDerivationImage() :
-  FGBase(DcmFGTypes::EFG_DERIVATIONIMAGE),
-  m_DerivationImageItems()
+FGDerivationImage::FGDerivationImage()
+    : FGBase(DcmFGTypes::EFG_DERIVATIONIMAGE)
+    , m_DerivationImageItems()
 {
 }
 
-
 FGDerivationImage::~FGDerivationImage()
 {
-  DcmIODUtil::freeContainer(m_DerivationImageItems);
+    DcmIODUtil::freeContainer(m_DerivationImageItems);
 }
 
-
 FGBase* FGDerivationImage::clone() const
 {
-  FGDerivationImage* copy = new FGDerivationImage();
-  if (copy)
-  {
-    OFVector<DerivationImageItem*>::const_iterator it = m_DerivationImageItems.begin();
-    while ( it != m_DerivationImageItems.end() )
+    OFunique_ptr<FGDerivationImage> copy(new FGDerivationImage);
+    if (copy)
     {
-      DerivationImageItem* itemCopy = new DerivationImageItem();
-      if (!itemCopy)
-      {
-        DCMFG_FATAL("Cannot clone FGDerivationImage: Memory exhausted");
-        return NULL;
-      }
-      *itemCopy = **it;
-      copy->getDerivationImageItems().push_back(itemCopy);
-      it++;
+        if (DcmIODUtil::copyContainer(this->m_DerivationImageItems, copy->m_DerivationImageItems).good())
+        {
+            return copy.release();
+        }
     }
-  }
-  return copy;
+    return OFnullptr;
 }
 
-
 FGDerivationImage* FGDerivationImage::createMinimal(const OFVector<ImageSOPInstanceReferenceMacro>& derivationImages,
                                                     const OFString& derivationDescription,
                                                     const CodeSequenceMacro& derivationCode,
                                                     const CodeSequenceMacro& purposeOfReference)
 {
-  OFCondition result;
-  FGDerivationImage* group = new FGDerivationImage();
-  if (group)
-  {
-    DerivationImageItem* derivItem = NULL;
-    result = group->addDerivationImageItem(derivationCode, derivationDescription, derivItem);
-    if (result.good())
+    OFCondition result;
+    FGDerivationImage* group = new FGDerivationImage();
+    if (group)
     {
-      OFVector<SourceImageItem*> srcImages = derivItem->getSourceImageItems();
-      OFVector<ImageSOPInstanceReferenceMacro>::const_iterator imageRef = derivationImages.begin();
-      while (imageRef != derivationImages.end())
-      {
-        SourceImageItem* item = new SourceImageItem();
-        if (item)
+        DerivationImageItem* derivItem = NULL;
+        result = group->addDerivationImageItem(derivationCode, derivationDescription, derivItem);
+        if (result.good())
         {
-          item->getPurposeOfReferenceCode() = purposeOfReference;
-          item->getImageSOPInstanceReference() = *imageRef;
-          derivItem->getSourceImageItems().push_back(item);
+            OFVector<SourceImageItem*> srcImages                              = derivItem->getSourceImageItems();
+            OFVector<ImageSOPInstanceReferenceMacro>::const_iterator imageRef = derivationImages.begin();
+            while (imageRef != derivationImages.end())
+            {
+                SourceImageItem* item = new SourceImageItem();
+                if (item)
+                {
+                    item->getPurposeOfReferenceCode()    = purposeOfReference;
+                    item->getImageSOPInstanceReference() = *imageRef;
+                    derivItem->getSourceImageItems().push_back(item);
+                }
+                else
+                {
+                    DCMFG_ERROR("Cannot create derivation description: Out of memory");
+                    result = EC_MemoryExhausted;
+                }
+                imageRef++;
+            }
         }
         else
         {
-          DCMFG_ERROR("Cannot create derivation description: Out of memory");
-          result = EC_MemoryExhausted;
+            DCMFG_ERROR("Cannot create derivation description: " << result.text());
         }
-        imageRef++;
-      }
     }
     else
     {
-      DCMFG_ERROR("Cannot create derivation description: " << result.text());
+        result = EC_MemoryExhausted;
     }
-  }
-  else
-  {
-    result = EC_MemoryExhausted;
-  }
 
-  if (result.bad())
-  {
-    delete group;
-    group = NULL;
-  }
+    if (result.bad())
+    {
+        delete group;
+        group = NULL;
+    }
 
-  return group;
+    return group;
 }
 
-
 int FGDerivationImage::compare(const FGBase& rhs) const
 {
-  int result = FGBase::compare(rhs);
-  if (result != 0)
-    return result;
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
 
-  const FGDerivationImage* myRhs = OFstatic_cast(const FGDerivationImage*, &rhs);
-  if (!myRhs)
-  {
-     return -1;
-  }
-
-  size_t thisSize = m_DerivationImageItems.size();
-  size_t rhsSize = myRhs->m_DerivationImageItems.size();
-  if (thisSize < rhsSize)
-  {
-    return 1;
-  }
-  else if (thisSize > rhsSize)
-  {
-    return -1;
-  }
+    const FGDerivationImage* myRhs = OFstatic_cast(const FGDerivationImage*, &rhs);
+    if (!myRhs)
+    {
+        return -1;
+    }
 
-  for (size_t count = 0; count < thisSize; count++)
-  {
-    int error = (*(m_DerivationImageItems[count])).compare( (*(myRhs->m_DerivationImageItems[count])) );
-    if (error != 0)
+    size_t thisSize = m_DerivationImageItems.size();
+    size_t rhsSize  = myRhs->m_DerivationImageItems.size();
+    if (thisSize < rhsSize)
+    {
+        return 1;
+    }
+    else if (thisSize > rhsSize)
     {
-      return error;
+        return -1;
     }
-  }
 
-  return 0;
+    for (size_t count = 0; count < thisSize; count++)
+    {
+        int error = (*(m_DerivationImageItems[count])).compare((*(myRhs->m_DerivationImageItems[count])));
+        if (error != 0)
+        {
+            return error;
+        }
+    }
 
+    return 0;
 }
 
-
 void FGDerivationImage::clearData()
 {
-  DcmIODUtil::freeContainer(m_DerivationImageItems);
+    DcmIODUtil::freeContainer(m_DerivationImageItems);
 }
 
-
 OFCondition FGDerivationImage::check() const
 {
-  OFCondition result;
-  OFVector<DerivationImageItem*>::const_iterator it = m_DerivationImageItems.begin();
-  while ( (it != m_DerivationImageItems.end()) && result.good() )
-  {
-    result = (*it)->check();
-    it++;
-  }
+    OFCondition result;
+    OFVector<DerivationImageItem*>::const_iterator it = m_DerivationImageItems.begin();
+    while ((it != m_DerivationImageItems.end()) && result.good())
+    {
+        result = (*it)->check();
+        it++;
+    }
 
-  return result;
+    return result;
 }
 
 DerivationImageItem& DerivationImageItem::operator=(const DerivationImageItem& rhs)
 {
-  m_DerivationDescription = rhs.m_DerivationDescription;
-  // Copy nested structures: Derivation Codes
-  OFVector<CodeSequenceMacro*>::const_iterator code = rhs.m_DerivationCodeItems.begin();
-  while ( code != rhs.m_DerivationCodeItems.end() )
-  {
-    m_DerivationCodeItems.push_back(new CodeSequenceMacro(**code));
-    code++;
-  }
-  // Copy nested structures: Derivation Codes
-  OFVector<SourceImageItem*>::const_iterator source = rhs.m_SourceImageItems.begin();
-  while ( source != rhs.m_SourceImageItems.end() )
-  {
-    m_SourceImageItems.push_back(new SourceImageItem(**source));
-    source++;
-  }
-  return *this;
+    m_DerivationDescription = rhs.m_DerivationDescription;
+    // Copy nested structures: Derivation Codes
+    OFVector<CodeSequenceMacro*>::const_iterator code = rhs.m_DerivationCodeItems.begin();
+    while (code != rhs.m_DerivationCodeItems.end())
+    {
+        m_DerivationCodeItems.push_back(new CodeSequenceMacro(**code));
+        code++;
+    }
+    // Copy nested structures: Derivation Codes
+    OFVector<SourceImageItem*>::const_iterator source = rhs.m_SourceImageItems.begin();
+    while (source != rhs.m_SourceImageItems.end())
+    {
+        m_SourceImageItems.push_back(new SourceImageItem(**source));
+        source++;
+    }
+    return *this;
 }
 
-
 OFCondition FGDerivationImage::addDerivationImageItem(const CodeSequenceMacro& derivationCode,
                                                       const OFString& derivationDescription,
                                                       DerivationImageItem*& item)
 {
-  OFCondition result;
-  item = new DerivationImageItem();
-  if (item == NULL)
-  {
-    return EC_MemoryExhausted;
-  }
-
-  // Initialize with given data
-  if (result.good())
-  {
-    result = item->setDerivationDescription(derivationDescription);
-  }
-  if (result.good())
-  {
-    item->getDerivationCodeItems().push_back(new CodeSequenceMacro(derivationCode));
-    m_DerivationImageItems.push_back(item);
-  }
-  else
-  {
-    delete item;
-    item = NULL;
-    result = FG_EC_InvalidData;
-  }
-  return result;
-}
+    OFCondition result;
+    item = new DerivationImageItem();
+    if (item == NULL)
+    {
+        return EC_MemoryExhausted;
+    }
 
+    // Initialize with given data
+    if (result.good())
+    {
+        result = item->setDerivationDescription(derivationDescription);
+    }
+    if (result.good())
+    {
+        item->getDerivationCodeItems().push_back(new CodeSequenceMacro(derivationCode));
+        m_DerivationImageItems.push_back(item);
+    }
+    else
+    {
+        delete item;
+        item   = NULL;
+        result = FG_EC_InvalidData;
+    }
+    return result;
+}
 
 OFVector<DerivationImageItem*>& FGDerivationImage::getDerivationImageItems()
 {
-  return m_DerivationImageItems;
+    return m_DerivationImageItems;
 }
 
-
 OFCondition FGDerivationImage::read(DcmItem& item)
 {
-  /* re-initialize object */
-  clearData();
+    /* re-initialize object */
+    clearData();
 
-  DcmSequenceOfItems *derivationImageSequence = NULL;
-  if (item.findAndGetSequence(DCM_DerivationImageSequence, derivationImageSequence).bad())
-    return FG_EC_NoSuchGroup;
+    DcmSequenceOfItems* derivationImageSequence = NULL;
+    if (item.findAndGetSequence(DCM_DerivationImageSequence, derivationImageSequence).bad())
+        return FG_EC_NoSuchGroup;
 
-  /* Read Derivation Image Sequence */
-  DcmIODUtil::readSubSequence<OFVector<DerivationImageItem*> >
-  ( derivationImageSequence,
-    DCM_DerivationImageSequence,
-    m_DerivationImageItems,
-    "0-n",
-    "2",
-    "DerivationImageMacro");
+    /* Read Derivation Image Sequence */
+    DcmIODUtil::readSubSequence<OFVector<DerivationImageItem*> >(derivationImageSequence,
+                                                                 DCM_DerivationImageSequence,
+                                                                 m_DerivationImageItems,
+                                                                 "0-n",
+                                                                 "2",
+                                                                 "DerivationImageMacro");
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 OFCondition FGDerivationImage::write(DcmItem& item)
 {
-  OFCondition result = check();
-  DcmIODUtil::writeSubSequence<OFVector<DerivationImageItem*> >
-  ( result,
-    DCM_DerivationImageSequence,
-    m_DerivationImageItems,
-    item,
-    "0-n",
-    "2",
-    "DerivationImageMacro" );
-  return result;
+    OFCondition result = check();
+    DcmIODUtil::writeSubSequence<OFVector<DerivationImageItem*> >(
+        result, DCM_DerivationImageSequence, m_DerivationImageItems, item, "0-n", "2", "DerivationImageMacro");
+    return result;
 }
 
-
 /* -- Class SourceImage Implementation -- */
 
 SourceImageItem::SourceImageItem()
-  : m_PurposeOfReferenceCode(),
-    m_ImageSOPInstanceReference()
+    : m_PurposeOfReferenceCode()
+    m_ImageSOPInstanceReference()
 {
 }
 
-
 SourceImageItem::~SourceImageItem()
 {
-  clearData();
+    clearData();
 }
 
-
 SourceImageItem& SourceImageItem::operator=(const SourceImageItem& rhs)
 {
-  m_PurposeOfReferenceCode = rhs.m_PurposeOfReferenceCode;
-  m_ImageSOPInstanceReference = rhs.m_ImageSOPInstanceReference;
-  return *this;
+    m_PurposeOfReferenceCode    = rhs.m_PurposeOfReferenceCode;
+    m_ImageSOPInstanceReference = rhs.m_ImageSOPInstanceReference;
+    return *this;
 }
 
-
 void SourceImageItem::clearData()
 {
-  m_PurposeOfReferenceCode.clearData();
-  m_ImageSOPInstanceReference.clear();
+    m_PurposeOfReferenceCode.clearData();
+    m_ImageSOPInstanceReference.clear();
 }
 
-
 OFCondition SourceImageItem::check() const
 {
-  OFCondition result = OFconst_cast(ImageSOPInstanceReferenceMacro*, &m_ImageSOPInstanceReference)->check();
-  if (result.bad())
-  {
-    return result;
-  }
+    OFCondition result = OFconst_cast(ImageSOPInstanceReferenceMacro*, &m_ImageSOPInstanceReference)->check();
+    if (result.bad())
+    {
+        return result;
+    }
 
-  return OFconst_cast(CodeSequenceMacro*, &m_PurposeOfReferenceCode)->check();
+    return OFconst_cast(CodeSequenceMacro*, &m_PurposeOfReferenceCode)->check();
 }
 
-
 int SourceImageItem::compare(const SourceImageItem& rhs) const
 {
-  int result = this->m_PurposeOfReferenceCode.compare(rhs.m_PurposeOfReferenceCode);
-  if (result != 0)
-  {
-    result = this->m_ImageSOPInstanceReference.compare(rhs.m_ImageSOPInstanceReference);
-  }
+    int result = this->m_PurposeOfReferenceCode.compare(rhs.m_PurposeOfReferenceCode);
+    if (result != 0)
+    {
+        result = this->m_ImageSOPInstanceReference.compare(rhs.m_ImageSOPInstanceReference);
+    }
 
-  return result;
+    return result;
 }
 
-
 CodeSequenceMacro& SourceImageItem::getPurposeOfReferenceCode()
 {
-  return m_PurposeOfReferenceCode;
+    return m_PurposeOfReferenceCode;
 }
 
-
 ImageSOPInstanceReferenceMacro& SourceImageItem::getImageSOPInstanceReference()
 {
-  return m_ImageSOPInstanceReference;
+    return m_ImageSOPInstanceReference;
 }
 
-
-OFCondition SourceImageItem::read(DcmItem& itemOfSourceImageSequence,
-                                  const OFBool clearOldData)
+OFCondition SourceImageItem::read(DcmItem& itemOfSourceImageSequence, const OFBool clearOldData)
 {
-  /* Re-initialize object */
-  if (clearOldData)
-    clearData();
+    /* Re-initialize object */
+    if (clearOldData)
+        clearData();
 
-  /* Read Purpose of Reference Code Sequence */
-  DcmIODUtil::readSingleItem<CodeSequenceMacro>(itemOfSourceImageSequence, DCM_PurposeOfReferenceCodeSequence, m_PurposeOfReferenceCode, "1", "DerivationImageMacro");
+    /* Read Purpose of Reference Code Sequence */
+    DcmIODUtil::readSingleItem<CodeSequenceMacro>(itemOfSourceImageSequence,
+                                                  DCM_PurposeOfReferenceCodeSequence,
+                                                  m_PurposeOfReferenceCode,
+                                                  "1",
+                                                  "DerivationImageMacro");
 
-  /* Read Source Image Sequence */
-  m_ImageSOPInstanceReference.read(itemOfSourceImageSequence);
+    /* Read Source Image Sequence */
+    m_ImageSOPInstanceReference.read(itemOfSourceImageSequence);
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 OFCondition SourceImageItem::write(DcmItem& itemOfSourceImageSequence)
 {
-  OFCondition result = EC_Normal;
+    OFCondition result = EC_Normal;
 
-  /* Write Purpose of Reference Code Sequence */
-  DcmIODUtil::writeSingleItem<CodeSequenceMacro>(result, DCM_PurposeOfReferenceCodeSequence, m_PurposeOfReferenceCode, itemOfSourceImageSequence, "1", "DerivationImageMacro");
+    /* Write Purpose of Reference Code Sequence */
+    DcmIODUtil::writeSingleItem<CodeSequenceMacro>(result,
+                                                   DCM_PurposeOfReferenceCodeSequence,
+                                                   m_PurposeOfReferenceCode,
+                                                   itemOfSourceImageSequence,
+                                                   "1",
+                                                   "DerivationImageMacro");
 
-  /* Write Image SOP Instance Reference Macro */
-  if ( result.good() )
-  {
-    m_ImageSOPInstanceReference.write(itemOfSourceImageSequence);
-  }
+    /* Write Image SOP Instance Reference Macro */
+    if (result.good())
+    {
+        m_ImageSOPInstanceReference.write(itemOfSourceImageSequence);
+    }
 
-  return result;
+    return result;
 }
 
-
 /* -- Class DerivationImageItem Implementation -- */
 
 DerivationImageItem::DerivationImageItem()
-  : m_DerivationDescription(DCM_DerivationDescription),
-    m_DerivationCodeItems(),
-    m_SourceImageItems()
+    : m_DerivationDescription(DCM_DerivationDescription)
+    , m_DerivationCodeItems()
+    m_SourceImageItems()
 {
 }
 
-
 DerivationImageItem::DerivationImageItem(const DerivationImageItem& rhs)
- : m_DerivationDescription(rhs.m_DerivationDescription),
-   m_DerivationCodeItems(),
-   m_SourceImageItems()
+    : m_DerivationDescription(rhs.m_DerivationDescription)
+    , m_DerivationCodeItems()
+    , m_SourceImageItems()
 {
-  OFVector<CodeSequenceMacro*>::const_iterator it = rhs.m_DerivationCodeItems.begin();
-  while (it != rhs.m_DerivationCodeItems.end())
-  {
-    CodeSequenceMacro* copy = new CodeSequenceMacro(**it);
-    if (!copy)
-    {
-      DCMFG_ERROR("Could not create copy of DerivationImageItem: Memory exhausted");
-      this->clearData();
-      return;
-    }
-    m_DerivationCodeItems.push_back(copy);
-    it++;
-  }
-
-  OFVector<SourceImageItem*>::const_iterator src = rhs.m_SourceImageItems.begin();
-  while (src != rhs.m_SourceImageItems.end())
-  {
-    SourceImageItem* copy = new SourceImageItem(**src);
-    if (!copy)
-    {
-      DCMFG_ERROR("Could not create copy of DerivationImageItem: Memory exhausted");
-      this->clearData();
-      return;
-    }
-    m_SourceImageItems.push_back(copy);
-    it++;
-  }
+    DcmIODUtil::copyContainer(rhs.m_DerivationCodeItems, this->m_DerivationCodeItems);
+    DcmIODUtil::copyContainer(rhs.m_SourceImageItems, this->m_SourceImageItems);
 }
 
-
 void DerivationImageItem::clearData()
 {
-  m_DerivationDescription.clear();
-  DcmIODUtil::freeContainer(m_DerivationCodeItems);
-  DcmIODUtil::freeContainer(m_SourceImageItems);
+    m_DerivationDescription.clear();
+    DcmIODUtil::freeContainer(m_DerivationCodeItems);
+    DcmIODUtil::freeContainer(m_SourceImageItems);
 }
 
-
 int DerivationImageItem::compare(const DerivationImageItem& rhs) const
 {
-  if (this == &rhs)
-    return OFTrue;
-
-  int result = m_DerivationDescription.compare(rhs.m_DerivationDescription);
-  if (result != 0) return result;
-
-  size_t numThis = m_DerivationCodeItems.size();
-  size_t numRhs = rhs.m_DerivationCodeItems.size();
-  size_t maxSize = (numThis > numRhs) ? numThis : numRhs;
-  for (size_t count = 0; count < maxSize; count++)
-  {
-    int error = (*m_DerivationCodeItems[count]).compare(*(rhs.m_DerivationCodeItems[count]));
-    if (error != 0)
-    {
-      return error;
-    }
-  }
-  if (numThis < numRhs)
-  {
-    return 1;
-  }
-  else if (numThis > numRhs)
-  {
-    return -1;
-  }
-
-  numThis = m_SourceImageItems.size();
-  numRhs = rhs.m_SourceImageItems.size();
-  maxSize = (numThis > numRhs) ? numThis : numRhs;
-  for (size_t count = 0; count < maxSize; count++)
-  {
-    int error = (*m_SourceImageItems[count]).compare(*(rhs.m_SourceImageItems[count]));
-    if (error != 0)
-    {
-      return error;
-    }
-  }
-  if (numThis < numRhs)
-  {
-    return 1;
-  }
-  else if (numThis > numRhs)
-  {
-    return -1;
-  }
-
-  // If we get here, the object values must be identical
-  return 0;
-}
+    if (this == &rhs)
+        return OFTrue;
+
+    int result = m_DerivationDescription.compare(rhs.m_DerivationDescription);
+    if (result != 0)
+        return result;
+
+    size_t numThis = m_DerivationCodeItems.size();
+    size_t numRhs  = rhs.m_DerivationCodeItems.size();
+    size_t maxSize = (numThis > numRhs) ? numThis : numRhs;
+    for (size_t count = 0; count < maxSize; count++)
+    {
+        int error = (*m_DerivationCodeItems[count]).compare(*(rhs.m_DerivationCodeItems[count]));
+        if (error != 0)
+        {
+            return error;
+        }
+    }
+    if (numThis < numRhs)
+    {
+        return 1;
+    }
+    else if (numThis > numRhs)
+    {
+        return -1;
+    }
 
+    numThis = m_SourceImageItems.size();
+    numRhs  = rhs.m_SourceImageItems.size();
+    maxSize = (numThis > numRhs) ? numThis : numRhs;
+    for (size_t count = 0; count < maxSize; count++)
+    {
+        int error = (*m_SourceImageItems[count]).compare(*(rhs.m_SourceImageItems[count]));
+        if (error != 0)
+        {
+            return error;
+        }
+    }
+    if (numThis < numRhs)
+    {
+        return 1;
+    }
+    else if (numThis > numRhs)
+    {
+        return -1;
+    }
+
+    // If we get here, the object values must be identical
+    return 0;
+}
 
 OFCondition DerivationImageItem::check() const
 {
-  if (m_DerivationCodeItems.size() == 0)
-  {
-    DCMFG_ERROR("Derivation Code Sequence in Derivation Image Functional Group Macro must have one or more items");
-    return FG_EC_InvalidData;
-  }
+    if (m_DerivationCodeItems.size() == 0)
+    {
+        DCMFG_ERROR("Derivation Code Sequence in Derivation Image Functional Group Macro must have one or more items");
+        return FG_EC_InvalidData;
+    }
 
-  OFCondition result;
-  OFVector<CodeSequenceMacro*>::const_iterator it = m_DerivationCodeItems.begin();
-  while (it != m_DerivationCodeItems.end() && result.good())
-  {
-    result = (*it)->check();
-    it++;
-  }
+    OFCondition result;
+    OFVector<CodeSequenceMacro*>::const_iterator it = m_DerivationCodeItems.begin();
+    while (it != m_DerivationCodeItems.end() && result.good())
+    {
+        result = (*it)->check();
+        it++;
+    }
 
-  OFVector<SourceImageItem*>::const_iterator ref = m_SourceImageItems.begin();
-  while ((ref != m_SourceImageItems.end()) && result.good())
-  {
-    result = (*ref)->check();
-    ref++;
-  }
-  return result;
+    OFVector<SourceImageItem*>::const_iterator ref = m_SourceImageItems.begin();
+    while ((ref != m_SourceImageItems.end()) && result.good())
+    {
+        result = (*ref)->check();
+        ref++;
+    }
+    return result;
 }
 
-
 DerivationImageItem::~DerivationImageItem()
 {
-  clearData();
+    clearData();
 }
 
-
 OFCondition DerivationImageItem::addSourceImageItem(const OFString& file,
                                                     const CodeSequenceMacro& purposeOfReference,
                                                     SourceImageItem*& resultSourceImageItem)
 {
-  DcmFileFormat dcmff;
-  DcmDataset *dataset = NULL;
-  OFCondition result = dcmff.loadFile(file.c_str());
-  if (result.bad())
-  {
-    DCMFG_ERROR("Could not load file " << file << ": " << result.text());
-    return result;
-  }
-  dataset = dcmff.getDataset();
-  return addSourceImageItem(dataset, purposeOfReference, resultSourceImageItem);
+    DcmFileFormat dcmff;
+    DcmDataset* dataset = NULL;
+    OFCondition result  = dcmff.loadFile(file.c_str());
+    if (result.bad())
+    {
+        DCMFG_ERROR("Could not load file " << file << ": " << result.text());
+        return result;
+    }
+    dataset = dcmff.getDataset();
+    return addSourceImageItem(dataset, purposeOfReference, resultSourceImageItem);
 }
 
-
-OFCondition DerivationImageItem::addSourceImageItem(DcmDataset *dataset,
+OFCondition DerivationImageItem::addSourceImageItem(DcmDataset* dataset,
                                                     const CodeSequenceMacro& purposeOfReference,
                                                     SourceImageItem*& resultSourceImageItem)
 {
-  // Create new source image item
-  SourceImageItem *item = new SourceImageItem();
-  if (item == NULL)
-  {
-    return EC_MemoryExhausted;
-  }
-
-  // check code validity
-  if ( OFconst_cast(CodeSequenceMacro*, &purposeOfReference)->check().bad() )
-  {
-    DCMFG_ERROR("Purpose of Reference code within item of Derivation Image Sequence is invalid");
-    return FG_EC_InvalidData;
-  }
-
-  item->getPurposeOfReferenceCode() = purposeOfReference;
-  resultSourceImageItem = NULL;
-  OFString sopClass, sopInstance, ts;
-  OFCondition result = DcmDataUtil::getSOPInstanceFromDataset(dataset, EXS_Unknown, sopClass, sopInstance, ts /*ignored*/);
-  {
-    if ( result.good() ) result = item->getImageSOPInstanceReference().setReferencedSOPClassUID(sopClass);
-    if ( result.good() ) result = item->getImageSOPInstanceReference().setReferencedSOPInstanceUID(sopInstance);
-  }
-  if (result.good())
-  {
-    m_SourceImageItems.push_back(item);
-    resultSourceImageItem = item;
-  }
-  else
-  {
-    delete item;
-  }
-
-  return result;
-}
-
-
-OFCondition DerivationImageItem::addSourceImageItems(const OFVector< OFString >& files,
+    // Create new source image item
+    SourceImageItem* item = new SourceImageItem();
+    if (item == NULL)
+    {
+        return EC_MemoryExhausted;
+    }
+
+    // check code validity
+    if (OFconst_cast(CodeSequenceMacro*, &purposeOfReference)->check().bad())
+    {
+        DCMFG_ERROR("Purpose of Reference code within item of Derivation Image Sequence is invalid");
+        return FG_EC_InvalidData;
+    }
+
+    item->getPurposeOfReferenceCode() = purposeOfReference;
+    resultSourceImageItem             = NULL;
+    OFString sopClass, sopInstance, ts;
+    OFCondition result
+        = DcmDataUtil::getSOPInstanceFromDataset(dataset, EXS_Unknown, sopClass, sopInstance, ts /*ignored*/);
+    {
+        if (result.good())
+            result = item->getImageSOPInstanceReference().setReferencedSOPClassUID(sopClass);
+        if (result.good())
+            result = item->getImageSOPInstanceReference().setReferencedSOPInstanceUID(sopInstance);
+    }
+    if (result.good())
+    {
+        m_SourceImageItems.push_back(item);
+        resultSourceImageItem = item;
+    }
+    else
+    {
+        delete item;
+    }
+
+    return result;
+}
+
+OFCondition DerivationImageItem::addSourceImageItems(const OFVector<OFString>& files,
                                                      const CodeSequenceMacro& purposeOfReference,
                                                      OFVector<SourceImageItem*>& resultSourceImageItems,
                                                      const OFBool skipErrors)
 {
-  DcmFileFormat dcmff;
-  OFCondition result;
-  DcmDataset *dataset = NULL;
-  OFVector<DcmDataset*> datasets;
-  OFVector<OFString>::const_iterator it = files.begin();
-  while (it != files.end())
-  {
-    result = dcmff.loadFile((*it).c_str());
-    if (result.bad())
+    DcmFileFormat dcmff;
+    OFCondition result;
+    DcmDataset* dataset = NULL;
+    OFVector<DcmDataset*> datasets;
+    OFVector<OFString>::const_iterator it = files.begin();
+    while (it != files.end())
     {
-      DCMFG_ERROR("Could not load file " << (*it) << ": " << result.text());
-      return result;
+        result = dcmff.loadFile((*it).c_str());
+        if (result.bad())
+        {
+            DCMFG_ERROR("Could not load file " << (*it) << ": " << result.text());
+            return result;
+        }
+        dataset = dcmff.getDataset();
+        datasets.push_back(dataset);
+        it++;
     }
-    dataset = dcmff.getDataset();
-    datasets.push_back(dataset);
-    it++;
-  }
-  return addSourceImageItems(datasets, purposeOfReference, resultSourceImageItems, skipErrors);
+    return addSourceImageItems(datasets, purposeOfReference, resultSourceImageItems, skipErrors);
 }
 
-
 OFCondition DerivationImageItem::addSourceImageItems(const OFVector<DcmDataset*>& datasets,
                                                      const CodeSequenceMacro& purposeOfReference,
                                                      OFVector<SourceImageItem*>& resultSourceImageItems,
                                                      const OFBool skipErrors)
-  {
-  OFCondition result;
-  OFVector<DcmDataset*>::const_iterator it = datasets.begin();
-  while (it != datasets.end())
-  {
-    SourceImageItem* resultItem = NULL;
-    result = addSourceImageItem((*it), purposeOfReference, resultItem);
-    if (result.good())
-    {
-      resultSourceImageItems.push_back(resultItem);
-    }
-    else if (result.bad() && !skipErrors)
-    {
-      DCMFG_ERROR("Could not add Source Image Sequence item for file " << *it << ": " << result.text());
-      break;
-    }
-    else if (result.bad())
+{
+    OFCondition result;
+    OFVector<DcmDataset*>::const_iterator it = datasets.begin();
+    while (it != datasets.end())
     {
-      DCMFG_WARN("Could not add Source Image Sequence item for file " << *it << ": " << result.text());
+        SourceImageItem* resultItem = NULL;
+        result                      = addSourceImageItem((*it), purposeOfReference, resultItem);
+        if (result.good())
+        {
+            resultSourceImageItems.push_back(resultItem);
+        }
+        else if (result.bad() && !skipErrors)
+        {
+            DCMFG_ERROR("Could not add Source Image Sequence item for file " << *it << ": " << result.text());
+            break;
+        }
+        else if (result.bad())
+        {
+            DCMFG_WARN("Could not add Source Image Sequence item for file " << *it << ": " << result.text());
+        }
+        it++;
     }
-    it++;
-  }
 
-  return result;
+    return result;
 }
 
-
 OFVector<CodeSequenceMacro*>& DerivationImageItem::getDerivationCodeItems()
 {
-  return m_DerivationCodeItems;
+    return m_DerivationCodeItems;
 }
 
-
-OFCondition DerivationImageItem::getDerivationDescription(OFString& value,
-                                                          const long signed int pos) const
+OFCondition DerivationImageItem::getDerivationDescription(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromElement(m_DerivationDescription, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_DerivationDescription, value, pos);
 }
 
-
-OFCondition DerivationImageItem::setDerivationDescription(const OFString& value,
-                                                          const OFBool checkValue)
+OFCondition DerivationImageItem::setDerivationDescription(const OFString& value, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_DerivationDescription.putOFStringArray(value);
+    (void)checkValue;
+    return m_DerivationDescription.putOFStringArray(value);
 }
 
-
 OFVector<SourceImageItem*>& DerivationImageItem::getSourceImageItems()
 {
-  return m_SourceImageItems;
+    return m_SourceImageItems;
 }
 
-
-OFCondition DerivationImageItem::read(DcmItem& itemOfDerivationImageSequence,
-                                      const OFBool clearOldData)
+OFCondition DerivationImageItem::read(DcmItem& itemOfDerivationImageSequence, const OFBool clearOldData)
 {
-  OFCondition result = EC_Normal;
+    OFCondition result = EC_Normal;
 
-  /* re-initialize object */
-  if (clearOldData)
-    clearData();
+    /* re-initialize object */
+    if (clearOldData)
+        clearData();
 
-  /* Derivation Description */
-  DcmIODUtil::getAndCheckElementFromDataset(itemOfDerivationImageSequence, m_DerivationDescription, "1" /* vm */, "3" /* type */, "DerivationImageMacro");
+    /* Derivation Description */
+    DcmIODUtil::getAndCheckElementFromDataset(
+        itemOfDerivationImageSequence, m_DerivationDescription, "1" /* vm */, "3" /* type */, "DerivationImageMacro");
 
-  /* Derivation Code Sequence */
-  DcmIODUtil::readSubSequence<OFVector<CodeSequenceMacro*> >
-  (  itemOfDerivationImageSequence,
-     DCM_DerivationCodeSequence,
-     m_DerivationCodeItems,
-     "1" /* vm */,
-     "3" /* type */,
-     "DerivationImageMacro" );
+    /* Derivation Code Sequence */
+    DcmIODUtil::readSubSequence<OFVector<CodeSequenceMacro*> >(itemOfDerivationImageSequence,
+                                                               DCM_DerivationCodeSequence,
+                                                               m_DerivationCodeItems,
+                                                               "1" /* vm */,
+                                                               "3" /* type */,
+                                                               "DerivationImageMacro");
 
-
-  /* Source Image Sequence */
-  DcmIODUtil::readSubSequence<OFVector<SourceImageItem*> >
-  ( itemOfDerivationImageSequence,
-    DCM_SourceImageSequence,
-    m_SourceImageItems,
-    "0-n" /* vm */,
-    "2" /* type */,
-    "DerivationImageMacro" );
+    /* Source Image Sequence */
+    DcmIODUtil::readSubSequence<OFVector<SourceImageItem*> >(itemOfDerivationImageSequence,
+                                                             DCM_SourceImageSequence,
+                                                             m_SourceImageItems,
+                                                             "0-n" /* vm */,
+                                                             "2" /* type */,
+                                                             "DerivationImageMacro");
 
     return result;
 }
 
-
 OFCondition DerivationImageItem::write(DcmItem& itemOfDerivationImageSequence)
 {
-  OFCondition result = EC_Normal;
+    OFCondition result = EC_Normal;
+
+    /* Write Derivation Description */
+    DcmIODUtil::copyElementToDataset(
+        result, itemOfDerivationImageSequence, m_DerivationDescription, "1", "3", "DerivationImageMacro");
+
+    /* Write Derivation Code Sequence */
+    DcmIODUtil::writeSubSequence<OFVector<CodeSequenceMacro*> >(result,
+                                                                DCM_DerivationCodeSequence,
+                                                                m_DerivationCodeItems,
+                                                                itemOfDerivationImageSequence,
+                                                                "1-n",
+                                                                "1",
+                                                                "DerivationImageMacro");
+
+    /* Write Source Image Sequence */
+    DcmIODUtil::writeSubSequence<OFVector<SourceImageItem*> >(result,
+                                                              DCM_SourceImageSequence,
+                                                              m_SourceImageItems,
+                                                              itemOfDerivationImageSequence,
+                                                              "0-n",
+                                                              "2",
+                                                              "DerivationImageMacro");
 
-  /* Write Derivation Description */
-  DcmIODUtil::copyElementToDataset(result, itemOfDerivationImageSequence, m_DerivationDescription, "1", "3", "DerivationImageMacro");
-
-  /* Write Derivation Code Sequence */
-  DcmIODUtil::writeSubSequence<OFVector<CodeSequenceMacro*> >
-  ( result,
-    DCM_DerivationCodeSequence,
-    m_DerivationCodeItems,
-    itemOfDerivationImageSequence,
-    "1-n",
-    "1",
-    "DerivationImageMacro" );
-
-  /* Write Source Image Sequence */
-  DcmIODUtil::writeSubSequence<OFVector<SourceImageItem*> >
-  ( result,
-    DCM_SourceImageSequence,
-    m_SourceImageItems,
-    itemOfDerivationImageSequence,
-    "0-n",
-    "2",
-    "DerivationImageMacro" );
-
-  return result;
+    return result;
 }
-
index a7146a93000219f1948893eb8d09b0b5b4907fa2..dfc051ea5810c3fd0c1f28f869d6eb31b30cb5b2 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2017, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  */
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmiod/iodutil.h"
-#include "dcmtk/dcmfg/fgfact.h"
+
+#include "dcmtk/dcmfg/fgctacquisitiondetails.h"
+#include "dcmtk/dcmfg/fgctacquisitiontype.h"
+#include "dcmtk/dcmfg/fgctadditionalxraysource.h"
+#include "dcmtk/dcmfg/fgctexposure.h"
+#include "dcmtk/dcmfg/fgctgeometry.h"
+#include "dcmtk/dcmfg/fgctimageframetype.h"
+#include "dcmtk/dcmfg/fgctposition.h"
+#include "dcmtk/dcmfg/fgctreconstruction.h"
+#include "dcmtk/dcmfg/fgcttabledynamics.h"
+#include "dcmtk/dcmfg/fgctxraydetails.h"
 #include "dcmtk/dcmfg/fgderimg.h"
+#include "dcmtk/dcmfg/fgfact.h"
 #include "dcmtk/dcmfg/fgfracon.h"
 #include "dcmtk/dcmfg/fgframeanatomy.h"
 #include "dcmtk/dcmfg/fgframevoilut.h"
-#include "dcmtk/dcmfg/fgpixeltransform.h"
 #include "dcmtk/dcmfg/fgimagedatatype.h"
+#include "dcmtk/dcmfg/fgirradiationeventid.h"
 #include "dcmtk/dcmfg/fgparametricmapframetype.h"
+#include "dcmtk/dcmfg/fgpixeltransform.h"
 #include "dcmtk/dcmfg/fgpixmsr.h"
 #include "dcmtk/dcmfg/fgplanor.h"
 #include "dcmtk/dcmfg/fgplanorvol.h"
 #include "dcmtk/dcmfg/fgplanpo.h"
 #include "dcmtk/dcmfg/fgplanposvol.h"
+#include "dcmtk/dcmfg/fgrealworldvaluemapping.h"
 #include "dcmtk/dcmfg/fgseg.h"
+#include "dcmtk/dcmfg/fgtemporalposition.h"
 #include "dcmtk/dcmfg/fgusimagedescription.h"
-#include "dcmtk/dcmfg/fgrealworldvaluemapping.h"
-
+#include "dcmtk/dcmiod/iodutil.h"
 
 FGFactory* FGFactory::m_Instance = NULL;
 
 FGFactory::FGFactory()
 {
-  // noting to do (private constructor)
+    // noting to do (private constructor)
 }
 
-
-
 FGFactory& FGFactory::instance()
 {
-  if (m_Instance == NULL)
-  {
-    m_Instance = new FGFactory();
-  }
-  return *m_Instance;
+    if (m_Instance == NULL)
+    {
+        m_Instance = new FGFactory();
+    }
+    return *m_Instance;
 }
 
-
 FGBase* FGFactory::create(const DcmFGTypes::E_FGType fgtype)
 {
-  switch(fgtype)
-  {
-    case DcmFGTypes::EFG_PIXELMEASURES:
-      return new FGPixelMeasures();
-      break;
-    case DcmFGTypes::EFG_FRAMEANATOMY:
-      return new FGFrameAnatomy();
-      break;
-    case DcmFGTypes::EFG_FRAMECONTENT:
-      return new FGFrameContent();
-      break;
-    case DcmFGTypes::EFG_FRAMEVOILUTMETA: // Frame VOI LUT and Frame VOI LUT with LUT
-      return new FGFrameVOILUT();
-      break;
-    case DcmFGTypes::EFG_PARAMETRICMAPFRAMETYPE:
-      return new FGParametricMapFrameType;
-      break;
-    case DcmFGTypes::EFG_PLANEPOSPATIENT:
-      return new FGPlanePosPatient();
-      break;
-    case DcmFGTypes::EFG_PLANEPOSITIONVOLUME:
-      return new FGPlanePositionVolume();
-    case DcmFGTypes::EFG_PLANEORIENTPATIENT:
-      return new FGPlaneOrientationPatient();
-      break;
-    case DcmFGTypes::EFG_PLANEORIENTVOLUME:
-      return new FGPlaneOrientationVolume();
-    case DcmFGTypes::EFG_DERIVATIONIMAGE:
-      return new FGDerivationImage();
-      break;
-    case DcmFGTypes::EFG_PIXELVALUETRANSMETA: // Pixel Value Transformation Macro or Identity Pixel Value Transformation Macro:
-      return new FGPixelValueTransformation();
-      break;
-    case DcmFGTypes::EFG_IMAGEDATATYPE:
-      return new FGImageDataType();
-      break;
-    case DcmFGTypes::EFG_REALWORLDVALUEMAPPING:
-      return new FGRealWorldValueMapping();
-      break;
-    case DcmFGTypes::EFG_SEGMENTATION:
-      return new FGSegmentation();
-      break;
-    case DcmFGTypes::EFG_USIMAGEDESCRIPTION:
-      return new FGUSImageDescription();
-      break;
-    case DcmFGTypes::EFG_CARDIACSYNC:
-    case DcmFGTypes::EFG_CONTRASTBOLUSUSAGE:
-    case DcmFGTypes::EFG_PIXELINTENSITYRELLUT:
-    case DcmFGTypes::EFG_FRAMEPIXELSHIFT:
-    case DcmFGTypes::EFG_PATIENTORIENTINFRAME:
-    case DcmFGTypes::EFG_FRAMEDISPLAYSHUTTER:
-    case DcmFGTypes::EFG_RESPIRATORYSYNC:
-    case DcmFGTypes::EFG_IRRADIATIONEVENTIDENT:
-    case DcmFGTypes::EFG_RADIOPHARAMAUSAGE:
-    case DcmFGTypes::EFG_PATIENTPHYSIOSTATE:
-    case DcmFGTypes::EFG_TEMPORALPOSITION:
-    {
-      DCMFG_DEBUG("Encountered functional group that is not explicitly supported yet:" << DcmFGTypes::FGType2OFString(fgtype));
-      return NULL;
-      break;
-    }
-    default:
+    switch (fgtype)
     {
-      DCMFG_DEBUG("Encountered unknown functional group");
-      return NULL;
-      break;
+        case DcmFGTypes::EFG_PIXELMEASURES:
+            return new FGPixelMeasures();
+            break;
+        case DcmFGTypes::EFG_FRAMEANATOMY:
+            return new FGFrameAnatomy();
+            break;
+        case DcmFGTypes::EFG_FRAMECONTENT:
+            return new FGFrameContent();
+            break;
+        case DcmFGTypes::EFG_CTACQUISITIONDETAILS:
+            return new FGCTAcquisitionDetails();
+            break;
+        case DcmFGTypes::EFG_CTACQUISITIONTYPE:
+            return new FGCTAcquisitionType();
+            break;
+        case DcmFGTypes::EFG_CTADDITIONALXRAYSOURCE:
+            return new FGCTAdditionalXRaySource();
+            break;
+        case DcmFGTypes::EFG_CTEXPOSURE:
+            return new FGCTExposure();
+            break;
+        case DcmFGTypes::EFG_CTGEOMETRY:
+            return new FGCTGeometry();
+            break;
+        case DcmFGTypes::EFG_CTIMAGEFRAMETYPE:
+            return new FGCTImageFrameType();
+            break;
+        case DcmFGTypes::EFG_CTPOSITION:
+            return new FGCTPosition();
+            break;
+        case DcmFGTypes::EFG_CTRECONSTRUCTION:
+            return new FGCTReconstruction();
+            break;
+        case DcmFGTypes::EFG_CTTABLEDYNAMICS:
+            return new FGCTTableDynamics();
+            break;
+        case DcmFGTypes::EFG_CTXRAYDETAILS:
+            return new FGCTXRayDetails();
+            break;
+        case DcmFGTypes::EFG_IRRADIATIONEVENTIDENT:
+            return new FGIrradiationEventIdentification();
+            break;
+        case DcmFGTypes::EFG_FRAMEVOILUTMETA: // Frame VOI LUT and Frame VOI LUT with LUT
+            return new FGFrameVOILUT();
+            break;
+        case DcmFGTypes::EFG_PARAMETRICMAPFRAMETYPE:
+            return new FGParametricMapFrameType;
+            break;
+        case DcmFGTypes::EFG_PLANEPOSPATIENT:
+            return new FGPlanePosPatient();
+            break;
+        case DcmFGTypes::EFG_PLANEPOSITIONVOLUME:
+            return new FGPlanePositionVolume();
+            break;
+        case DcmFGTypes::EFG_PLANEORIENTPATIENT:
+            return new FGPlaneOrientationPatient();
+            break;
+        case DcmFGTypes::EFG_PLANEORIENTVOLUME:
+            return new FGPlaneOrientationVolume();
+        case DcmFGTypes::EFG_DERIVATIONIMAGE:
+            return new FGDerivationImage();
+            break;
+        case DcmFGTypes::EFG_PIXELVALUETRANSMETA: // Pixel Value Transformation Macro or Identity Pixel Value
+                                                  // Transformation Macro:
+            return new FGPixelValueTransformation();
+            break;
+        case DcmFGTypes::EFG_IMAGEDATATYPE:
+            return new FGImageDataType();
+            break;
+        case DcmFGTypes::EFG_REALWORLDVALUEMAPPING:
+            return new FGRealWorldValueMapping();
+            break;
+        case DcmFGTypes::EFG_SEGMENTATION:
+            return new FGSegmentation();
+            break;
+        case DcmFGTypes::EFG_TEMPORALPOSITION:
+            return new FGTemporalPosition();
+            break;
+        case DcmFGTypes::EFG_USIMAGEDESCRIPTION:
+            return new FGUSImageDescription();
+            break;
+        case DcmFGTypes::EFG_CARDIACSYNC:
+        case DcmFGTypes::EFG_CONTRASTBOLUSUSAGE:
+        case DcmFGTypes::EFG_PIXELINTENSITYRELLUT:
+        case DcmFGTypes::EFG_FRAMEPIXELSHIFT:
+        case DcmFGTypes::EFG_PATIENTORIENTINFRAME:
+        case DcmFGTypes::EFG_FRAMEDISPLAYSHUTTER:
+        case DcmFGTypes::EFG_RESPIRATORYSYNC:
+        case DcmFGTypes::EFG_RADIOPHARAMAUSAGE:
+        case DcmFGTypes::EFG_PATIENTPHYSIOSTATE:
+        {
+            DCMFG_DEBUG("Encountered functional group that is not explicitly supported yet:"
+                        << DcmFGTypes::FGType2OFString(fgtype));
+            return NULL;
+            break;
+        }
+        default:
+        {
+            DCMFG_DEBUG("Encountered unknown functional group");
+            return NULL;
+            break;
+        }
     }
-  }
-  return NULL;
+    return NULL;
 }
 
-
 FGBase* FGFactory::create(const DcmTagKey& fgSequenceKey)
 {
-  if (!DcmIODUtil::isSequenceTag(fgSequenceKey))
-  {
-    DCMFG_ERROR("Cannot create functional group from non-sequence tag");
-    return NULL;
-  }
-  FGBase* fg = NULL;
-  DcmFGTypes::E_FGType fgType = DcmFGTypes::tagKey2FGType(fgSequenceKey);
-  if (fgType != DcmFGTypes::EFG_UNKNOWN)
-  {
-    fg = create(fgType);
-  }
-  /* if the sequence is know but there is no specific implementation, create generic functional group */
-  if (fg == NULL)
-  {
-    DCMFG_DEBUG("Encountered unknown functional group, started by tag key: " << fgSequenceKey);
-    fg = new FGUnknown(fgSequenceKey);
-  }
-  return fg;
+    if (!DcmIODUtil::isSequenceTag(fgSequenceKey))
+    {
+        DCMFG_ERROR("Cannot create functional group from non-sequence tag");
+        return NULL;
+    }
+    FGBase* fg                  = NULL;
+    DcmFGTypes::E_FGType fgType = DcmFGTypes::tagKey2FGType(fgSequenceKey);
+    if (fgType != DcmFGTypes::EFG_UNKNOWN)
+    {
+        fg = create(fgType);
+    }
+    /* if the sequence is know but there is no specific implementation, create generic functional group */
+    if (fg == NULL)
+    {
+        DCMFG_DEBUG("Encountered unknown functional group, started by tag key: " << fgSequenceKey);
+        fg = new FGUnknown(fgSequenceKey);
+    }
+    return fg;
 }
index e24a4c354ea22629894b722e6071263a21731a29..133a7cb2010e96f2174de632a3bd2ba9fc52817f 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  */
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcdeftag.h"
-#include "dcmtk/dcmiod/iodutil.h"
 #include "dcmtk/dcmfg/fgfracon.h"
 #include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/dcmiod/iodutil.h"
 
 // Constructor
-FGFrameContent::FGFrameContent() :
-  FGBase(DcmFGTypes::EFG_FRAMECONTENT),
-  m_FrameAcquisitonNumber(DCM_FrameAcquisitionNumber),
-  m_FrameReferenceDateTime(DCM_FrameReferenceDateTime),
-  m_FrameAcquisitionDateTime(DCM_FrameAcquisitionDateTime),
-  m_FrameAcquisitionDuration(DCM_FrameAcquisitionDuration),
-  m_CardiacCyclePosition(DCM_CardiacCyclePosition),
-  m_RespiratoryCyclePosition(DCM_RespiratoryCyclePosition),
-  m_DimensionIndexValues(DCM_DimensionIndexValues),
-  m_TemporalPositionIndex(DCM_TemporalPositionIndex),
-  m_StackID(DCM_StackID),
-  m_InStackPositionNumber(DCM_InStackPositionNumber),
-  m_FrameComments(DCM_FrameComments),
-  m_FrameLabel(DCM_FrameLabel)
+FGFrameContent::FGFrameContent()
+    : FGBase(DcmFGTypes::EFG_FRAMECONTENT)
+    , m_FrameAcquisitonNumber(DCM_FrameAcquisitionNumber)
+    , m_FrameReferenceDateTime(DCM_FrameReferenceDateTime)
+    , m_FrameAcquisitionDateTime(DCM_FrameAcquisitionDateTime)
+    , m_FrameAcquisitionDuration(DCM_FrameAcquisitionDuration)
+    , m_CardiacCyclePosition(DCM_CardiacCyclePosition)
+    , m_RespiratoryCyclePosition(DCM_RespiratoryCyclePosition)
+    , m_DimensionIndexValues(DCM_DimensionIndexValues)
+    , m_TemporalPositionIndex(DCM_TemporalPositionIndex)
+    , m_StackID(DCM_StackID)
+    , m_InStackPositionNumber(DCM_InStackPositionNumber)
+    , m_FrameComments(DCM_FrameComments)
+    , m_FrameLabel(DCM_FrameLabel)
 {
 }
 
-
 FGFrameContent::~FGFrameContent()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
 FGBase* FGFrameContent::clone() const
 {
-  FGFrameContent* copy = new FGFrameContent();
-  if (copy)
-  {
-    copy->m_FrameAcquisitonNumber = this->m_FrameAcquisitonNumber;
-    copy->m_FrameReferenceDateTime = this->m_FrameReferenceDateTime;
-    copy->m_FrameAcquisitionDateTime = this->m_FrameAcquisitionDateTime;
-    copy->m_FrameAcquisitionDuration = this->m_FrameAcquisitionDuration;
-    copy->m_CardiacCyclePosition = this->m_CardiacCyclePosition;
-    copy->m_RespiratoryCyclePosition = this->m_RespiratoryCyclePosition;
-    copy->m_DimensionIndexValues = this->m_DimensionIndexValues;
-    copy->m_TemporalPositionIndex = this->m_TemporalPositionIndex;
-    copy->m_StackID = this->m_StackID;
-    copy->m_InStackPositionNumber = this->m_InStackPositionNumber;
-    copy->m_FrameComments = this->m_FrameComments;
-    copy->m_FrameLabel = this->m_FrameLabel;
-  }
-  return copy;
+    FGFrameContent* copy = new FGFrameContent();
+    if (copy)
+    {
+        copy->m_FrameAcquisitonNumber    = this->m_FrameAcquisitonNumber;
+        copy->m_FrameReferenceDateTime   = this->m_FrameReferenceDateTime;
+        copy->m_FrameAcquisitionDateTime = this->m_FrameAcquisitionDateTime;
+        copy->m_FrameAcquisitionDuration = this->m_FrameAcquisitionDuration;
+        copy->m_CardiacCyclePosition     = this->m_CardiacCyclePosition;
+        copy->m_RespiratoryCyclePosition = this->m_RespiratoryCyclePosition;
+        copy->m_DimensionIndexValues     = this->m_DimensionIndexValues;
+        copy->m_TemporalPositionIndex    = this->m_TemporalPositionIndex;
+        copy->m_StackID                  = this->m_StackID;
+        copy->m_InStackPositionNumber    = this->m_InStackPositionNumber;
+        copy->m_FrameComments            = this->m_FrameComments;
+        copy->m_FrameLabel               = this->m_FrameLabel;
+    }
+    return copy;
 }
 
-
 void FGFrameContent::clearData()
 {
-  m_FrameAcquisitonNumber.clear();
-  m_FrameReferenceDateTime.clear();
-  m_FrameAcquisitionDateTime.clear();
-  m_FrameAcquisitionDuration.clear();
-  m_CardiacCyclePosition.clear();
-  m_RespiratoryCyclePosition.clear();
-  m_DimensionIndexValues.clear();
-  m_TemporalPositionIndex.clear();
-  m_StackID.clear();
-  m_InStackPositionNumber.clear();
-  m_FrameComments.clear();
-  m_FrameLabel.clear();
+    m_FrameAcquisitonNumber.clear();
+    m_FrameReferenceDateTime.clear();
+    m_FrameAcquisitionDateTime.clear();
+    m_FrameAcquisitionDuration.clear();
+    m_CardiacCyclePosition.clear();
+    m_RespiratoryCyclePosition.clear();
+    m_DimensionIndexValues.clear();
+    m_TemporalPositionIndex.clear();
+    m_StackID.clear();
+    m_InStackPositionNumber.clear();
+    m_FrameComments.clear();
+    m_FrameLabel.clear();
 }
 
-
 OFCondition FGFrameContent::check() const
 {
-  // Maybe add checks later
-  return EC_Normal;
+    // Maybe add checks later
+    return EC_Normal;
 }
 
-
 /// Read Frame Content Sequence from given item
 OFCondition FGFrameContent::read(DcmItem& item)
 {
-  clearData();
-
-  DcmItem* seqItem = NULL;
-  OFCondition result = getItemFromFGSequence(item, DCM_FrameContentSequence, 0, seqItem);
-  if (result.bad())
-    return result;
+    clearData();
 
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FrameAcquisitonNumber, "1", "3", "FrameContentMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FrameReferenceDateTime, "1", "1C", "FrameContentMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FrameAcquisitionDateTime, "1", "1C", "FrameContentMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FrameAcquisitionDuration, "1", "1C", "FrameContentMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_CardiacCyclePosition, "1", "3", "FrameContentMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_RespiratoryCyclePosition, "1", "3", "FrameContentMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_DimensionIndexValues, "1-n", "1C", "FrameContentMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_TemporalPositionIndex, "1", "1C", "FrameContentMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_StackID, "1", "1C", "FrameContentMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_InStackPositionNumber, "1", "1C", "FrameContentMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FrameComments, "1", "3", "FrameContentMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FrameLabel, "1", "3", "FrameContentMacro");
+    DcmItem* seqItem   = NULL;
+    OFCondition result = getItemFromFGSequence(item, DCM_FrameContentSequence, 0, seqItem);
+    if (result.bad())
+        return result;
 
-  return EC_Normal;
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FrameAcquisitonNumber, "1", "3", "FrameContentMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FrameReferenceDateTime, "1", "1C", "FrameContentMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FrameAcquisitionDateTime, "1", "1C", "FrameContentMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FrameAcquisitionDuration, "1", "1C", "FrameContentMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_CardiacCyclePosition, "1", "3", "FrameContentMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_RespiratoryCyclePosition, "1", "3", "FrameContentMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_DimensionIndexValues, "1-n", "1C", "FrameContentMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_TemporalPositionIndex, "1", "1C", "FrameContentMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_StackID, "1", "1C", "FrameContentMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_InStackPositionNumber, "1", "1C", "FrameContentMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FrameComments, "1", "3", "FrameContentMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FrameLabel, "1", "3", "FrameContentMacro");
 
+    return EC_Normal;
 }
 
 /// Writes single Frame Content Sequence into given item
 OFCondition FGFrameContent::write(DcmItem& item)
 {
-  DcmItem *seqItem = NULL;
-  OFCondition result = createNewFGSequence(item, DCM_FrameContentSequence, 0, seqItem);
-  if (result.bad())
+    DcmItem* seqItem   = NULL;
+    OFCondition result = createNewFGSequence(item, DCM_FrameContentSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+
+    // --- write frame content macro attributes ---
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_FrameAcquisitonNumber, "1", "3", "FrameContentMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_FrameReferenceDateTime, "1", "1C", "FrameContentMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_FrameAcquisitionDateTime, "1", "1C", "FrameContentMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_FrameAcquisitionDuration, "1", "1C", "FrameContentMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_CardiacCyclePosition, "1", "3", "FrameContentMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_RespiratoryCyclePosition, "1", "3", "FrameContentMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_DimensionIndexValues, "1-n", "1C", "FrameContentMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_TemporalPositionIndex, "1", "1C", "FrameContentMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_StackID, "1", "1C", "FrameContentMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_InStackPositionNumber, "1", "1C", "FrameContentMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_FrameComments, "1", "3", "FrameContentMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_FrameLabel, "1", "3", "FrameContentMacro");
     return result;
-
-  // --- write frame content macro attributes ---
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_FrameAcquisitonNumber, "1", "3", "FrameContentMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_FrameReferenceDateTime, "1", "1C", "FrameContentMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_FrameAcquisitionDateTime, "1", "1C", "FrameContentMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_FrameAcquisitionDuration, "1", "1C", "FrameContentMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_CardiacCyclePosition, "1", "3", "FrameContentMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_RespiratoryCyclePosition, "1", "3", "FrameContentMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_DimensionIndexValues, "1-n", "1C", "FrameContentMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_TemporalPositionIndex, "1", "1C", "FrameContentMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_StackID, "1", "1C", "FrameContentMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_InStackPositionNumber, "1", "1C", "FrameContentMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_FrameComments, "1", "3", "FrameContentMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_FrameLabel, "1", "3", "FrameContentMacro");
-  return result;
 }
 
-
 int FGFrameContent::compare(const FGBase& rhs) const
 {
-  int result = FGBase::compare(rhs);
-  if (result != 0)
-    return result;
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
+
+    const FGFrameContent* myRhs = OFstatic_cast(const FGFrameContent*, &rhs);
+    if (!myRhs)
+        return -1;
+
+    // Compare all elements
+    result = m_FrameAcquisitonNumber.compare(myRhs->m_FrameAcquisitonNumber);
+    if (result == 0)
+        result = m_FrameReferenceDateTime.compare(myRhs->m_FrameReferenceDateTime);
+    if (result == 0)
+        result = m_FrameAcquisitionDateTime.compare(myRhs->m_FrameAcquisitionDateTime);
+    if (result == 0)
+        result = m_FrameAcquisitionDuration.compare(myRhs->m_FrameAcquisitionDuration);
+    if (result == 0)
+        result = m_CardiacCyclePosition.compare(myRhs->m_CardiacCyclePosition);
+    if (result == 0)
+        result = m_RespiratoryCyclePosition.compare(myRhs->m_RespiratoryCyclePosition);
+    if (result == 0)
+        result = m_DimensionIndexValues.compare(myRhs->m_DimensionIndexValues);
+    if (result == 0)
+        result = m_TemporalPositionIndex.compare(myRhs->m_TemporalPositionIndex);
+    if (result == 0)
+        result = m_StackID.compare(myRhs->m_StackID);
+    if (result == 0)
+        result = m_InStackPositionNumber.compare(myRhs->m_InStackPositionNumber);
+    if (result == 0)
+        result = m_FrameComments.compare(myRhs->m_FrameComments);
+    if (result == 0)
+        result = m_FrameLabel.compare(myRhs->m_FrameLabel);
 
-  const FGFrameContent* myRhs = OFstatic_cast(const FGFrameContent*, &rhs);
-  if (!myRhs)
-    return -1;
-
-  // Compare all elements
-  result = m_FrameAcquisitonNumber.compare(myRhs->m_FrameAcquisitonNumber);
-  if (result == 0)
-    result = m_FrameReferenceDateTime.compare(myRhs->m_FrameReferenceDateTime);
-  if (result == 0)
-    result = m_FrameAcquisitionDateTime.compare(myRhs->m_FrameAcquisitionDateTime);
-  if (result == 0)
-    result = m_FrameAcquisitionDuration.compare(myRhs->m_FrameAcquisitionDuration);
-  if (result == 0)
-    result = m_CardiacCyclePosition.compare(myRhs->m_CardiacCyclePosition);
-  if (result == 0)
-    result = m_RespiratoryCyclePosition.compare(myRhs->m_RespiratoryCyclePosition);
-  if (result == 0)
-    result = m_DimensionIndexValues.compare(myRhs->m_DimensionIndexValues);
-  if (result == 0)
-    result = m_TemporalPositionIndex.compare(myRhs->m_TemporalPositionIndex);
-  if (result == 0)
-    result = m_StackID.compare(myRhs->m_StackID);
-  if (result == 0)
-    result = m_InStackPositionNumber.compare(myRhs->m_InStackPositionNumber);
-  if (result == 0)
-    result = m_FrameComments.compare(myRhs->m_FrameComments);
-  if (result == 0)
-    result = m_FrameLabel.compare(myRhs->m_FrameLabel);
-
-  return result;
+    return result;
 }
 
-
 // --- get() functionality ---
 
-OFCondition FGFrameContent::getFrameAcquisitionNumber(Uint16& value,
-                                                      const signed long pos)
+OFCondition FGFrameContent::getFrameAcquisitionNumber(Uint16& value, const unsigned long pos)
 {
-  return m_FrameAcquisitonNumber.getUint16(value, pos);
+    return m_FrameAcquisitonNumber.getUint16(value, pos);
 }
 
-OFCondition FGFrameContent::getFrameReferenceDateTime(OFString& value,
-                                                      const signed long pos)
+OFCondition FGFrameContent::getFrameReferenceDateTime(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_FrameReferenceDateTime, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_FrameReferenceDateTime, value, pos);
 }
 
-OFCondition FGFrameContent::getFrameAcquisitionDateTime(OFString& value,
-                                                        const signed long pos)
+OFCondition FGFrameContent::getFrameAcquisitionDateTime(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_FrameAcquisitionDateTime, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_FrameAcquisitionDateTime, value, pos);
 }
 
-OFCondition FGFrameContent::getFrameAcquisitionDuration(Float64& value,
-                                                        const unsigned long pos)
+OFCondition FGFrameContent::getFrameAcquisitionDuration(Float64& value, const unsigned long pos)
 {
-  return m_FrameAcquisitionDuration.getFloat64(value, pos);
+    return m_FrameAcquisitionDuration.getFloat64(value, pos);
 }
 
-OFCondition FGFrameContent::getCardiacCyclePosition(OFString& value,
-                                                    const signed long pos)
+OFCondition FGFrameContent::getCardiacCyclePosition(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_CardiacCyclePosition, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_CardiacCyclePosition, value, pos);
 }
 
-OFCondition FGFrameContent::getRespiratoryCyclePosition(OFString& value,
-                                                        const signed long pos)
+OFCondition FGFrameContent::getRespiratoryCyclePosition(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_RespiratoryCyclePosition, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_RespiratoryCyclePosition, value, pos);
 }
 
-OFCondition FGFrameContent::getDimensionIndexValues(Uint32& value,
-                                                    const signed long pos)
+OFCondition FGFrameContent::getDimensionIndexValues(Uint32& value, const unsigned long pos)
 {
-  return m_DimensionIndexValues.getUint32(value, pos);
+    return m_DimensionIndexValues.getUint32(value, pos);
 }
 
-OFCondition FGFrameContent::getTemporalPositionIndex(Uint32& value,
-                                                     const signed long pos)
+OFCondition FGFrameContent::getTemporalPositionIndex(Uint32& value, const unsigned long pos)
 {
-  return m_TemporalPositionIndex.getUint32(value, pos);
+    return m_TemporalPositionIndex.getUint32(value, pos);
 }
 
-OFCondition FGFrameContent::getStackID(OFString& value,
-                                       const signed long pos)
+OFCondition FGFrameContent::getStackID(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_StackID, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_StackID, value, pos);
 }
 
-OFCondition FGFrameContent::getInStackPositionNumber(Uint32& value,
-                                                     const long signed int pos)
+OFCondition FGFrameContent::getInStackPositionNumber(Uint32& value, const unsigned long pos)
 {
-  return m_InStackPositionNumber.getUint32(value, pos);
+    return m_InStackPositionNumber.getUint32(value, pos);
 }
 
-
-OFCondition FGFrameContent::getFrameComments(OFString& value,
-                                             const signed long pos)
+OFCondition FGFrameContent::getFrameComments(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_FrameComments, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_FrameComments, value, pos);
 }
 
-OFCondition FGFrameContent::getFrameLabel(OFString& value,
-                                          const signed long pos)
+OFCondition FGFrameContent::getFrameLabel(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_FrameLabel, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_FrameLabel, value, pos);
 }
 
 // --- set() functionality ---
 
-OFCondition FGFrameContent::setFrameAcquisitionNumber(const Uint16& value,
-                                                      const OFBool checkValue)
+OFCondition FGFrameContent::setFrameAcquisitionNumber(const Uint16& value, const OFBool checkValue)
 {
-  (void)checkValue;
-  m_FrameAcquisitonNumber.putUint16(value);
-  return EC_Normal;
+    (void)checkValue;
+    m_FrameAcquisitonNumber.putUint16(value);
+    return EC_Normal;
 }
 
-OFCondition FGFrameContent::setFrameReferenceDateTime(const OFString& value,
-                                                      const OFBool checkValue)
+OFCondition FGFrameContent::setFrameReferenceDateTime(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDateTime::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_FrameReferenceDateTime.putOFStringArray(value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDateTime::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_FrameReferenceDateTime.putOFStringArray(value);
+    return result;
 }
 
-OFCondition FGFrameContent::setFrameAcquisitionDateTime(const OFString& value,
-                                                        const OFBool checkValue)
+OFCondition FGFrameContent::setFrameAcquisitionDateTime(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDateTime::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_FrameAcquisitionDateTime.putOFStringArray(value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDateTime::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_FrameAcquisitionDateTime.putOFStringArray(value);
+    return result;
 }
 
-OFCondition FGFrameContent::setFrameAcquisitionDuration(const Float64& value,
-                                                        const OFBool checkValue)
+OFCondition FGFrameContent::setFrameAcquisitionDuration(const Float64& value, const OFBool checkValue)
 {
-  (void)checkValue;
-  // basic checking always included
-  return m_FrameAcquisitionDuration.putFloat64(value);
+    (void)checkValue;
+    // basic checking always included
+    return m_FrameAcquisitionDuration.putFloat64(value);
 }
 
-OFCondition FGFrameContent::setCardiacCyclePosition(const OFString& value,
-                                                    const OFBool checkValue)
+OFCondition FGFrameContent::setCardiacCyclePosition(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_CardiacCyclePosition.putOFStringArray(value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_CardiacCyclePosition.putOFStringArray(value);
+    return result;
 }
 
-OFCondition FGFrameContent::setRespiratoryCyclePosition(const OFString& value,
-                                                        const OFBool checkValue)
+OFCondition FGFrameContent::setRespiratoryCyclePosition(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_RespiratoryCyclePosition.putOFStringArray(value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_RespiratoryCyclePosition.putOFStringArray(value);
+    return result;
 }
 
-OFCondition FGFrameContent::setDimensionIndexValues(const Uint32& value,
-                                                    const unsigned int dim,
-                                                    const OFBool checkValue)
+OFCondition
+FGFrameContent::setDimensionIndexValues(const Uint32& value, const unsigned int dim, const OFBool checkValue)
 {
-  // no other meaningful checks possible in this context
-  (void)checkValue;
-  if (value == 0)
-  {
-    DCMFG_ERROR("Cannot set dimension index value 0, must be >= 1)");
-    return EC_InvalidValue;
-  }
-  return m_DimensionIndexValues.putUint32(value, dim);
+    // no other meaningful checks possible in this context
+    (void)checkValue;
+    if (value == 0)
+    {
+        DCMFG_ERROR("Cannot set dimension index value 0, must be >= 1)");
+        return EC_InvalidValue;
+    }
+    return m_DimensionIndexValues.putUint32(value, dim);
 }
 
-OFCondition FGFrameContent::setTemporalPositionIndex(const Uint32& value,
-                                                     const OFBool checkValue)
+OFCondition FGFrameContent::setTemporalPositionIndex(const Uint32& value, const OFBool checkValue)
 {
-  // no meaningful check possible in this context
-  (void)checkValue;
-  return m_TemporalPositionIndex.putUint32(value);
+    // no meaningful check possible in this context
+    (void)checkValue;
+    return m_TemporalPositionIndex.putUint32(value);
 }
 
-OFCondition FGFrameContent::setStackID(const OFString& value,
-                                       const OFBool checkValue)
+OFCondition FGFrameContent::setStackID(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_StackID.putOFStringArray(value);
-  return result;
+    OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_StackID.putOFStringArray(value);
+    return result;
 }
 
-
-OFCondition FGFrameContent::setInStackPositionNumber(const Uint32& value,
-                                                     const OFBool checkValue)
+OFCondition FGFrameContent::setInStackPositionNumber(const Uint32& value, const OFBool checkValue)
 {
-  // no meaningful check possible in this context
-  (void)checkValue;
-  return m_InStackPositionNumber.putUint32(value);
+    // no meaningful check possible in this context
+    (void)checkValue;
+    return m_InStackPositionNumber.putUint32(value);
 }
 
-
-OFCondition FGFrameContent::setFrameComments(const OFString& value,
-                                             const OFBool checkValue)
+OFCondition FGFrameContent::setFrameComments(const OFString& value, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_FrameComments.putOFStringArray(value);
+    (void)checkValue;
+    return m_FrameComments.putOFStringArray(value);
 }
 
-
-OFCondition FGFrameContent::setFrameLabel(const OFString& value,
-                                          const OFBool checkValue)
+OFCondition FGFrameContent::setFrameLabel(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_FrameLabel.putOFStringArray(value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_FrameLabel.putOFStringArray(value);
+    return result;
 }
-
index 22a9ea413260c21296c91ea01ca45a261eaa8756..57e7a40ed6a667a9ecdf4a2af18cbafc776918e4 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmfg/fgframeanatomy.h"
+
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgframeanatomy.h"
 #include "dcmtk/dcmiod/iodutil.h"
 
-
 FGFrameAnatomy::FGFrameAnatomy()
-: FGBase(DcmFGTypes::EFG_FRAMEANATOMY),
-  m_FrameLaterality(LATERALITY_UNDEFINED),
-  m_Anatomy("1" /* Use Mandatory version of macro, i.e. make "Anatomic Region Sequence type 1" */)
+    : FGBase(DcmFGTypes::EFG_FRAMEANATOMY)
+    , m_FrameLaterality(LATERALITY_UNDEFINED)
+    , m_Anatomy("1" /* Use Mandatory version of macro, i.e. make "Anatomic Region Sequence type 1" */)
 {
 }
 
-
 FGFrameAnatomy::~FGFrameAnatomy()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
 FGBase* FGFrameAnatomy::clone() const
 {
-  FGFrameAnatomy* copy = new FGFrameAnatomy();
-  if (copy)
-  {
-    copy->m_FrameLaterality= this->m_FrameLaterality;
-    copy->m_Anatomy = this->m_Anatomy;
-  }
-  return copy;
+    FGFrameAnatomy* copy = new FGFrameAnatomy();
+    if (copy)
+    {
+        copy->m_FrameLaterality = this->m_FrameLaterality;
+        copy->m_Anatomy         = this->m_Anatomy;
+    }
+    return copy;
 }
 
-
 void FGFrameAnatomy::clearData()
 {
-  m_FrameLaterality = LATERALITY_UNDEFINED;
-  m_Anatomy.clearData();
+    m_FrameLaterality = LATERALITY_UNDEFINED;
+    m_Anatomy.clearData();
 }
 
-
 OFCondition FGFrameAnatomy::check() const
 {
-  if (!isLateralityValid(m_FrameLaterality))
-  {
-    DCMFG_ERROR("Frame Laterality invalid");
-    return FG_EC_InvalidData;
-  }
-  return OFconst_cast(GeneralAnatomyMacro*, &m_Anatomy)->check();
+    if (!isLateralityValid(m_FrameLaterality))
+    {
+        DCMFG_ERROR("Frame Laterality invalid");
+        return FG_EC_InvalidData;
+    }
+    return OFconst_cast(GeneralAnatomyMacro*, &m_Anatomy)->check();
 }
 
-
 int FGFrameAnatomy::compare(const FGBase& rhs) const
 {
-  int result = FGBase::compare(rhs);
-  if (result != 0)
-    return result;
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
 
-  const FGFrameAnatomy* myRhs = OFstatic_cast(const FGFrameAnatomy*, &rhs);
-  if (!myRhs)
-    return -1;
+    const FGFrameAnatomy* myRhs = OFstatic_cast(const FGFrameAnatomy*, &rhs);
+    if (!myRhs)
+        return -1;
 
-  // Compare all elements
-  if (m_FrameLaterality != myRhs->m_FrameLaterality)
-    return 1;
+    // Compare all elements
+    if (m_FrameLaterality != myRhs->m_FrameLaterality)
+        return 1;
 
-  return m_Anatomy.compare(myRhs->m_Anatomy);
+    return m_Anatomy.compare(myRhs->m_Anatomy);
 }
 
-
 /// Read from Frame Content Sequence
 OFCondition FGFrameAnatomy::read(DcmItem& item)
 {
-  clearData();
+    clearData();
 
-  OFCondition result;
-  DcmItem* seqItem = NULL;
-  result = getItemFromFGSequence(item, DCM_FrameAnatomySequence, 0, seqItem);
-  if (result.bad())
-    return result;
+    OFCondition result;
+    DcmItem* seqItem = NULL;
+    result           = getItemFromFGSequence(item, DCM_FrameAnatomySequence, 0, seqItem);
+    if (result.bad())
+        return result;
 
-  DcmCodeString elem(DCM_FrameLaterality);
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, elem,   "1", "1", "FrameAnatomyMacro");
-  OFString val;
-  elem.getOFStringArray(val);
-  m_FrameLaterality = str2Laterality(val);
+    DcmCodeString elem(DCM_FrameLaterality);
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, elem, "1", "1", "FrameAnatomyMacro");
+    OFString val;
+    elem.getOFStringArray(val);
+    m_FrameLaterality = str2Laterality(val);
 
-  m_Anatomy.read(*seqItem);
+    m_Anatomy.read(*seqItem);
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 OFCondition FGFrameAnatomy::write(DcmItem& item)
 {
-  OFCondition result = check();
-  if (result.good())
-  {
-    DcmItem* seqItem = NULL;
-    result = createNewFGSequence(item, DCM_FrameAnatomySequence, 0, seqItem);
+    OFCondition result = check();
     if (result.good())
     {
-      OFString lat = laterality2Str(m_FrameLaterality);
-      result = seqItem->putAndInsertOFStringArray(DCM_FrameLaterality, lat);
-      if (result.good())
-      {
-        result = m_Anatomy.write(*seqItem);
-      }
+        DcmItem* seqItem = NULL;
+        result           = createNewFGSequence(item, DCM_FrameAnatomySequence, 0, seqItem);
+        if (result.good())
+        {
+            OFString lat = laterality2Str(m_FrameLaterality);
+            result       = seqItem->putAndInsertOFStringArray(DCM_FrameLaterality, lat);
+            if (result.good())
+            {
+                result = m_Anatomy.write(*seqItem);
+            }
+        }
     }
-  }
 
-  return result;
+    return result;
 }
 
-
 OFCondition FGFrameAnatomy::getLaterality(FGFrameAnatomy::LATERALITY& value)
 {
-  value = m_FrameLaterality;
-  return EC_Normal;
+    value = m_FrameLaterality;
+    return EC_Normal;
 }
 
-
 GeneralAnatomyMacro& FGFrameAnatomy::getAnatomy()
 {
-  return m_Anatomy;
+    return m_Anatomy;
 }
 
-
 OFCondition FGFrameAnatomy::setLaterality(const FGFrameAnatomy::LATERALITY& value)
 {
-  if (isLateralityValid(value))
-  {
-    m_FrameLaterality = value;
-    return EC_Normal;
-  }
-  else
-  {
-    return FG_EC_InvalidData;
-  }
+    if (isLateralityValid(value))
+    {
+        m_FrameLaterality = value;
+        return EC_Normal;
+    }
+    else
+    {
+        return FG_EC_InvalidData;
+    }
 }
 
-
 OFString FGFrameAnatomy::laterality2Str(const FGFrameAnatomy::LATERALITY lat)
 {
-  switch(lat)
-  {
-    case LATERALITY_INVALID: return "Invalid";
-    case LATERALITY_L: return "L";
-    case LATERALITY_R: return "R";
-    case LATERALITY_BOTH: return "B";
-    case LATERALITY_UNDEFINED: return "Undefined";
-    case LATERALITY_UNPAIRED: return "U";
-    default: return "Invalid";
-  }
+    switch (lat)
+    {
+        case LATERALITY_INVALID:
+            return "Invalid";
+        case LATERALITY_L:
+            return "L";
+        case LATERALITY_R:
+            return "R";
+        case LATERALITY_BOTH:
+            return "B";
+        case LATERALITY_UNDEFINED:
+            return "Undefined";
+        case LATERALITY_UNPAIRED:
+            return "U";
+        default:
+            return "Invalid";
+    }
 }
 
-
 FGFrameAnatomy::LATERALITY FGFrameAnatomy::str2Laterality(const OFString& lat)
 {
-  if (lat == "L")
-    return LATERALITY_L;
-  if (lat == "R")
-    return LATERALITY_R;
-  if (lat == "U")
-    return LATERALITY_UNPAIRED;
-  if (lat == "B")
-    return LATERALITY_BOTH;
-
-  if (lat.empty())
-    return LATERALITY_UNDEFINED;
-
-  return LATERALITY_INVALID;
-
+    if (lat == "L")
+        return LATERALITY_L;
+    if (lat == "R")
+        return LATERALITY_R;
+    if (lat == "U")
+        return LATERALITY_UNPAIRED;
+    if (lat == "B")
+        return LATERALITY_BOTH;
+
+    if (lat.empty())
+        return LATERALITY_UNDEFINED;
+
+    return LATERALITY_INVALID;
 }
 
-
 OFBool FGFrameAnatomy::isLateralityValid(const FGFrameAnatomy::LATERALITY lat)
 {
-  if ( (lat == LATERALITY_L) || (lat == LATERALITY_R) || (lat == LATERALITY_BOTH) ||
-       (lat == LATERALITY_UNPAIRED) )
-    return OFTrue;
-  else
-    return OFFalse;
+    if ((lat == LATERALITY_L) || (lat == LATERALITY_R) || (lat == LATERALITY_BOTH) || (lat == LATERALITY_UNPAIRED))
+        return OFTrue;
+    else
+        return OFFalse;
 }
-
index 9a85ba5431976314d148f580c22390a4ca7fca1f..214fe9cc0de329aad699d5481a7cc8291c6d358d 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  */
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcdeftag.h"
-#include "dcmtk/dcmiod/iodutil.h"
 #include "dcmtk/dcmfg/fgframevoilut.h"
 #include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/dcmiod/iodutil.h"
+
+const OFString FGFrameVOILUT::DT_CT_WindowCenterWidthExplanation_Brain      = "BRAIN";
+const OFString FGFrameVOILUT::DT_CT_WindowCenterWidthExplanation_SoftTissue = "SOFT_TISSUE";
+const OFString FGFrameVOILUT::DT_CT_WindowCenterWidthExplanation_Lung       = "LUNG";
+const OFString FGFrameVOILUT::DT_CT_WindowCenterWidthExplanation_Bone       = "BONE";
 
 // Constructor
-FGFrameVOILUT::FGFrameVOILUT() :
-  FGBase(DcmFGTypes::EFG_FRAMEVOILUTMETA),
-  m_WindowCenter(DCM_WindowCenter),
-  m_WindowWidth(DCM_WindowWidth),
-  m_WindowCenterWindowWidthExplanation(DCM_WindowCenterWidthExplanation),
-  m_VOILUTFunction(DCM_VOILUTFunction)
+FGFrameVOILUT::FGFrameVOILUT()
+    : FGBase(DcmFGTypes::EFG_FRAMEVOILUTMETA)
+    , m_WindowCenter(DCM_WindowCenter)
+    , m_WindowWidth(DCM_WindowWidth)
+    , m_WindowCenterWindowWidthExplanation(DCM_WindowCenterWidthExplanation)
+    , m_VOILUTFunction(DCM_VOILUTFunction)
 {
 }
 
-
 FGFrameVOILUT::~FGFrameVOILUT()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
 FGBase* FGFrameVOILUT::clone() const
 {
-  FGFrameVOILUT* copy = new FGFrameVOILUT();
-  if (copy)
-  {
-    copy->m_WindowCenter = this->m_WindowCenter;
-    copy->m_WindowWidth= this->m_WindowWidth;
-    copy->m_WindowCenterWindowWidthExplanation = this->m_WindowCenterWindowWidthExplanation;
-    copy->m_VOILUTFunction= this->m_VOILUTFunction;
-  }
-  return copy;
+    FGFrameVOILUT* copy = new FGFrameVOILUT();
+    if (copy)
+    {
+        copy->m_WindowCenter                       = this->m_WindowCenter;
+        copy->m_WindowWidth                        = this->m_WindowWidth;
+        copy->m_WindowCenterWindowWidthExplanation = this->m_WindowCenterWindowWidthExplanation;
+        copy->m_VOILUTFunction                     = this->m_VOILUTFunction;
+    }
+    return copy;
 }
 
-
 void FGFrameVOILUT::clearData()
 {
-  m_WindowCenter.clear();
-  m_WindowWidth.clear();
-  m_WindowCenterWindowWidthExplanation.clear();
-  m_VOILUTFunction.clear();
+    m_WindowCenter.clear();
+    m_WindowWidth.clear();
+    m_WindowCenterWindowWidthExplanation.clear();
+    m_VOILUTFunction.clear();
 }
 
-
 OFCondition FGFrameVOILUT::check() const
 {
-  // For now attribute-based checks in read() and write() are sufficient
-  return EC_Normal;
+    // For now attribute-based checks in read() and write() are sufficient
+    return EC_Normal;
 }
 
-
 // --- get() functionality ---
 
-
-OFCondition FGFrameVOILUT::getWindowCenter(Float64& value,
-                                           const unsigned long pos)
+OFCondition FGFrameVOILUT::getWindowCenter(Float64& value, const unsigned long pos)
 {
-  return m_WindowCenter.getFloat64(value, pos);
+    return m_WindowCenter.getFloat64(value, pos);
 }
 
-
-OFCondition FGFrameVOILUT::getWindowWidth(Float64& value,
-                                          const unsigned long pos)
+OFCondition FGFrameVOILUT::getWindowWidth(Float64& value, const unsigned long pos)
 {
-  return m_WindowWidth.getFloat64(value, pos);
+    return m_WindowWidth.getFloat64(value, pos);
 }
 
-
-OFCondition FGFrameVOILUT::getWindowCenterAndWindowWidthExplanation(OFString& value,
-                                                                    const unsigned long pos)
+OFCondition FGFrameVOILUT::getWindowCenterAndWindowWidthExplanation(OFString& value, const unsigned long pos)
 {
-  return m_WindowCenterWindowWidthExplanation.getOFString(value, pos);
+    return m_WindowCenterWindowWidthExplanation.getOFString(value, pos);
 }
 
-
-OFCondition FGFrameVOILUT::getCenterWidthExplanation(Float64& windowCenter,
-                                                     Float64& windowWidth,
-                                                     OFString& explanation)
+OFCondition FGFrameVOILUT::getCenterWidthExplanation(Float64& windowCenter, Float64& windowWidth, OFString& explanation)
 {
-  OFCondition result = m_WindowCenter.getFloat64(windowCenter);
-  if (result.good()) result = m_WindowWidth.getFloat64(windowWidth);
-  if (result.good()) result = m_WindowCenterWindowWidthExplanation.getOFString(explanation, 0);
-  return result;
+    OFCondition result = m_WindowCenter.getFloat64(windowCenter);
+    if (result.good())
+        result = m_WindowWidth.getFloat64(windowWidth);
+    if (result.good())
+        result = m_WindowCenterWindowWidthExplanation.getOFString(explanation, 0);
+    return result;
 }
 
-
-OFCondition FGFrameVOILUT::getVOILUTFunction(OFString& value,
-                                             const unsigned long pos)
+OFCondition FGFrameVOILUT::getVOILUTFunction(OFString& value, const unsigned long pos)
 {
-  return m_VOILUTFunction.getOFString(value, pos);
+    return m_VOILUTFunction.getOFString(value, pos);
 }
 
-
 // --- set() functionality ---
 
-
-OFCondition FGFrameVOILUT::setWindowCenter(const OFString& value,
-                                           const OFBool checkValue)
+OFCondition FGFrameVOILUT::setWindowCenter(const OFString& value, const OFBool checkValue)
 {
-  // no checks at the moment
-  (void)checkValue;
-  return m_WindowCenter.putOFStringArray(value);
+    // no checks at the moment
+    (void)checkValue;
+    return m_WindowCenter.putOFStringArray(value);
 }
 
-OFCondition FGFrameVOILUT::setWindowWidth(const OFString& value,
-                                          const OFBool checkValue)
+OFCondition FGFrameVOILUT::setWindowWidth(const OFString& value, const OFBool checkValue)
 {
-  // no checks at the moment
-  (void)checkValue;
-  return m_WindowWidth.putOFStringArray(value);
+    // no checks at the moment
+    (void)checkValue;
+    return m_WindowWidth.putOFStringArray(value);
 }
 
-
 OFCondition FGFrameVOILUT::setCenterWidthExplanation(const Float64& windowCenter,
                                                      const Float64& windowWidth,
                                                      const OFString& explanation,
                                                      const OFBool checkValue)
 {
-  OFCondition result = m_WindowCenter.putFloat64(windowCenter);
-  if (result.good()) result = m_WindowWidth.putFloat64(windowWidth);
-  if (result.good() && !explanation.empty())
-  {
-    if (checkValue)
-    {
-      result = (checkValue) ? DcmLongString::checkStringValue(explanation, "1") : EC_Normal;
-    }
+    OFCondition result = m_WindowCenter.putFloat64(windowCenter);
     if (result.good())
+        result = m_WindowWidth.putFloat64(windowWidth);
+    if (result.good() && !explanation.empty())
     {
-      result = m_WindowCenterWindowWidthExplanation.putString(explanation.c_str());
+        if (checkValue)
+        {
+            result = (checkValue) ? DcmLongString::checkStringValue(explanation, "1") : EC_Normal;
+        }
+        if (result.good())
+        {
+            result = m_WindowCenterWindowWidthExplanation.putString(explanation.c_str());
+        }
     }
-  }
-  return result;
+    return result;
 }
 
-
-OFCondition FGFrameVOILUT::setVOILUTFunction(const OFString& value,
-                                             const OFBool checkValue)
+OFCondition FGFrameVOILUT::setVOILUTFunction(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_VOILUTFunction.putString(value.c_str());
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_VOILUTFunction.putString(value.c_str());
+    return result;
 }
 
-
 /// Read Frame Content Sequence from given item
 OFCondition FGFrameVOILUT::read(DcmItem& item)
 {
-  clearData();
-
-  DcmItem* seqItem = NULL;
-  OFCondition result = getItemFromFGSequence(item, DCM_FrameVOILUTSequence, 0, seqItem);
-  if (result.bad())
-    return result;
+    clearData();
 
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_WindowCenter, "1-n", "1", "FrameVOILUTMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_WindowWidth, "1-n", "1", "FrameVOILUTMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_WindowCenterWindowWidthExplanation, "1-n", "3", "FrameVOILUTMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_VOILUTFunction, "1", "3", "FrameVOILUTMacro");
+    DcmItem* seqItem   = NULL;
+    OFCondition result = getItemFromFGSequence(item, DCM_FrameVOILUTSequence, 0, seqItem);
+    if (result.bad())
+        return result;
 
-  return EC_Normal;
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_WindowCenter, "1-n", "1", "FrameVOILUTMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_WindowWidth, "1-n", "1", "FrameVOILUTMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(
+        *seqItem, m_WindowCenterWindowWidthExplanation, "1-n", "3", "FrameVOILUTMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_VOILUTFunction, "1", "3", "FrameVOILUTMacro");
 
+    return EC_Normal;
 }
 
 /// Writes single Frame Content Sequence into given item
 OFCondition FGFrameVOILUT::write(DcmItem& item)
 {
-  DcmItem *seqItem = NULL;
-  OFCondition result = createNewFGSequence(item, DCM_FrameVOILUTSequence, 0, seqItem);
-  if (result.bad())
+    DcmItem* seqItem   = NULL;
+    OFCondition result = createNewFGSequence(item, DCM_FrameVOILUTSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+
+    // --- write frame content macro attributes ---
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_WindowCenter, "1-n", "1", "FrameVOILUTMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_WindowWidth, "1-n", "1", "FrameVOILUTMacro");
+    DcmIODUtil::copyElementToDataset(
+        result, *seqItem, m_WindowCenterWindowWidthExplanation, "1-n", "3", "FrameVOILUTMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_VOILUTFunction, "1", "3", "FrameVOILUTMacro");
     return result;
-
-  // --- write frame content macro attributes ---
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_WindowCenter, "1-n", "1", "FrameVOILUTMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_WindowWidth, "1-n", "1", "FrameVOILUTMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_WindowCenterWindowWidthExplanation, "1-n", "3", "FrameVOILUTMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_VOILUTFunction, "1", "3", "FrameVOILUTMacro");
-  return result;
 }
 
-
 int FGFrameVOILUT::compare(const FGBase& rhs) const
 {
-  int result = FGBase::compare(rhs);
-  if (result != 0)
-    return result;
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
 
-  const FGFrameVOILUT* myRhs = OFstatic_cast(const FGFrameVOILUT*, &rhs);
-  if (!myRhs)
-    return -1;
+    const FGFrameVOILUT* myRhs = OFstatic_cast(const FGFrameVOILUT*, &rhs);
+    if (!myRhs)
+        return -1;
 
-  // Compare all elements
-  result = m_WindowCenter.compare(myRhs->m_WindowCenter);
-  if (result == 0)
-    result = m_WindowWidth.compare(myRhs->m_WindowWidth);
-  if (result == 0)
-    result = m_WindowCenterWindowWidthExplanation.compare(myRhs->m_WindowCenterWindowWidthExplanation);
-  if (result == 0)
-    result = m_VOILUTFunction.compare(myRhs->m_VOILUTFunction);
+    // Compare all elements
+    result = m_WindowCenter.compare(myRhs->m_WindowCenter);
+    if (result == 0)
+        result = m_WindowWidth.compare(myRhs->m_WindowWidth);
+    if (result == 0)
+        result = m_WindowCenterWindowWidthExplanation.compare(myRhs->m_WindowCenterWindowWidthExplanation);
+    if (result == 0)
+        result = m_VOILUTFunction.compare(myRhs->m_VOILUTFunction);
 
-  return result;
+    return result;
 }
index 782ee4435a82bd918f86bee42f513444f9570174..a3b81db2b7b83f1a061fc3b94e467833c5a26c9a 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  */
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcdeftag.h"
-#include "dcmtk/dcmiod/iodutil.h"
 #include "dcmtk/dcmfg/fgimagedatatype.h"
 #include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/dcmiod/iodutil.h"
 
 // Constructor
-FGImageDataType::FGImageDataType() :
-  FGBase(DcmFGTypes::EFG_IMAGEDATATYPE),
-  m_DataType(DCM_DataType),
-  m_AliasedDataType(DCM_AliasedDataType),
-  m_ZeroVelocityPixelValueUS(DCM_ZeroVelocityPixelValue),
-  m_ZeroVelocityPixelValueSS(DCM_ZeroVelocityPixelValue)
+FGImageDataType::FGImageDataType()
+    : FGBase(DcmFGTypes::EFG_IMAGEDATATYPE)
+    , m_DataType(DCM_DataType)
+    , m_AliasedDataType(DCM_AliasedDataType)
+    , m_ZeroVelocityPixelValueUS(DCM_ZeroVelocityPixelValue)
+    , m_ZeroVelocityPixelValueSS(DCM_ZeroVelocityPixelValue)
 {
 }
 
-
 FGImageDataType::~FGImageDataType()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
 FGBase* FGImageDataType::clone() const
 {
-  FGImageDataType* copy = new FGImageDataType();
-  if (copy)
-  {
-    copy->m_DataType = this->m_DataType;
-    copy->m_AliasedDataType= this->m_AliasedDataType;
-    if (! OFconst_cast(DcmSignedShort*, &this->m_ZeroVelocityPixelValueSS)->isEmpty())
-    {
-      copy->m_ZeroVelocityPixelValueSS = this->m_ZeroVelocityPixelValueSS;
-    }
-    else if (! OFconst_cast(DcmUnsignedShort*, &this->m_ZeroVelocityPixelValueUS)->isEmpty())
+    FGImageDataType* copy = new FGImageDataType();
+    if (copy)
     {
-      copy->m_ZeroVelocityPixelValueUS = this->m_ZeroVelocityPixelValueUS;
+        copy->m_DataType        = this->m_DataType;
+        copy->m_AliasedDataType = this->m_AliasedDataType;
+        if (!OFconst_cast(DcmSignedShort*, &this->m_ZeroVelocityPixelValueSS)->isEmpty())
+        {
+            copy->m_ZeroVelocityPixelValueSS = this->m_ZeroVelocityPixelValueSS;
+        }
+        else if (!OFconst_cast(DcmUnsignedShort*, &this->m_ZeroVelocityPixelValueUS)->isEmpty())
+        {
+            copy->m_ZeroVelocityPixelValueUS = this->m_ZeroVelocityPixelValueUS;
+        }
+        // both emtpy? nothing to do then
     }
-    // both emtpy? nothing to do then
-  }
-  return copy;
+    return copy;
 }
 
-
 void FGImageDataType::clearData()
 {
-  m_DataType.clear();
-  m_AliasedDataType.clear();
-  m_ZeroVelocityPixelValueSS.clear();
-  m_ZeroVelocityPixelValueUS.clear();
+    m_DataType.clear();
+    m_AliasedDataType.clear();
+    m_ZeroVelocityPixelValueSS.clear();
+    m_ZeroVelocityPixelValueUS.clear();
 }
 
-
 OFCondition FGImageDataType::check() const
 {
-   // For now, checks in read() and write() are sufficient
-  return EC_Normal;
+    // For now, checks in read() and write() are sufficient
+    return EC_Normal;
 }
 
-
 // --- get() functionality ---
 
-OFCondition FGImageDataType::getDataType(OFString& value,
-                                         const long signed int pos)
+OFCondition FGImageDataType::getDataType(OFString& value, const long signed int pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_DataType, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_DataType, value, pos);
 }
 
-
 OFCondition FGImageDataType::getAliasedDataType(OFString& value, const long signed int pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_AliasedDataType, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_AliasedDataType, value, pos);
 }
 
-
-OFCondition FGImageDataType::getZeroVelocityPixelValue(Sint32& value,
-                                                       const long signed int pos)
+OFCondition FGImageDataType::getZeroVelocityPixelValue(Sint32& value, const unsigned long pos)
 {
-  OFCondition result;
-  if (!m_ZeroVelocityPixelValueSS.isEmpty())
-  {
-    Sint16 val = 0;
-    if ( (result = m_ZeroVelocityPixelValueSS.getSint16(val, pos)).good())
+    OFCondition result;
+    if (!m_ZeroVelocityPixelValueSS.isEmpty())
     {
-      value = val;
+        Sint16 val = 0;
+        if ((result = m_ZeroVelocityPixelValueSS.getSint16(val, pos)).good())
+        {
+            value = val;
+        }
     }
-  }
-  else if (!m_ZeroVelocityPixelValueUS.isEmpty())
-  {
-    Uint16 val = 0;
-    if ( (result = m_ZeroVelocityPixelValueUS.getUint16(val, pos)).good())
+    else if (!m_ZeroVelocityPixelValueUS.isEmpty())
     {
-      value = val;
+        Uint16 val = 0;
+        if ((result = m_ZeroVelocityPixelValueUS.getUint16(val, pos)).good())
+        {
+            value = val;
+        }
     }
-  }
-  else
-    return EC_TagNotFound;
+    else
+        return EC_TagNotFound;
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 // --- set() functionality ---
 
-
-OFCondition FGImageDataType::setDataType(const OFString& value,
-                                         const OFBool checkValue)
+OFCondition FGImageDataType::setDataType(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_DataType.putOFStringArray(value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_DataType.putOFStringArray(value);
+    return result;
 }
 
-
-OFCondition FGImageDataType::setAliasedDataType(const OFString& value,
-                                                const OFBool checkValue)
+OFCondition FGImageDataType::setAliasedDataType(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_AliasedDataType.putOFStringArray(value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_AliasedDataType.putOFStringArray(value);
+    return result;
 }
 
-
 OFCondition FGImageDataType::setZeroVelocityPixelValueSS(const Sint16 value)
 {
-  return m_ZeroVelocityPixelValueSS.putSint16(value);
+    return m_ZeroVelocityPixelValueSS.putSint16(value);
 }
 
-
 OFCondition FGImageDataType::setZeroVelocityPixelValueUS(const Uint16 value)
 {
-  return m_ZeroVelocityPixelValueUS.putUint16(value);
+    return m_ZeroVelocityPixelValueUS.putUint16(value);
 }
 
-
 // Read Frame Content Sequence from given item
 OFCondition FGImageDataType::read(DcmItem& item)
 {
-  clearData();
-
-  DcmItem* seqItem = NULL;
-  OFCondition result = getItemFromFGSequence(item, DCM_ImageDataTypeSequence, 0, seqItem);
-  if (result.bad())
-    return result;
-
-  DcmElement* elem = NULL;
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_DataType, "1", "1", "ImageDataTypeMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_AliasedDataType, "1", "1", "ImageDataTypeMacro");
-  // We do not know the VR of Zero Velocity Pixel Value (US or SS), so we cannot
-  // use the regular getAndCheckElementFromDataset() method that implicitly gets
-  // this information via the provided element. Instead, get element first and
-  // and then check it in an extra step, afterwards access value depending on
-  // the element's VR.
-  seqItem->findAndGetElement(DCM_ZeroVelocityPixelValue, elem);
-  DcmIODUtil::checkElementValue(elem, DCM_ZeroVelocityPixelValue, "1", "1C", EC_Normal, "ImageDataTypeMacro");
-  if (elem)
-  {
-    if (elem->getVR() == EVR_SS)
-    {
-      m_ZeroVelocityPixelValueSS.copyFrom(*elem);
-    }
-    else if (elem->getVR() == EVR_US)
-    {
-      m_ZeroVelocityPixelValueUS.copyFrom(*elem);
-    }
-    else
+    clearData();
+
+    DcmItem* seqItem   = NULL;
+    OFCondition result = getItemFromFGSequence(item, DCM_ImageDataTypeSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+
+    DcmElement* elem = NULL;
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_DataType, "1", "1", "ImageDataTypeMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_AliasedDataType, "1", "1", "ImageDataTypeMacro");
+    // We do not know the VR of Zero Velocity Pixel Value (US or SS), so we cannot
+    // use the regular getAndCheckElementFromDataset() method that implicitly gets
+    // this information via the provided element. Instead, get element first and
+    // and then check it in an extra step, afterwards access value depending on
+    // the element's VR.
+    seqItem->findAndGetElement(DCM_ZeroVelocityPixelValue, elem);
+    DcmIODUtil::checkElementValue(elem, DCM_ZeroVelocityPixelValue, "1", "1C", EC_Normal, "ImageDataTypeMacro");
+    if (elem)
     {
-      Uint16 pixrep = 0;
-      if (item.findAndGetUint16(DCM_PixelRepresentation, pixrep).good())
-      {
-        if (pixrep == 0)
+        if (elem->getVR() == EVR_SS)
+        {
+            m_ZeroVelocityPixelValueSS.copyFrom(*elem);
+        }
+        else if (elem->getVR() == EVR_US)
         {
-          m_ZeroVelocityPixelValueUS.putUint16(pixrep, 0);
+            m_ZeroVelocityPixelValueUS.copyFrom(*elem);
         }
         else
         {
-          m_ZeroVelocityPixelValueSS.putSint16(pixrep, 1);
+            Uint16 pixrep = 0;
+            if (item.findAndGetUint16(DCM_PixelRepresentation, pixrep).good())
+            {
+                if (pixrep == 0)
+                {
+                    m_ZeroVelocityPixelValueUS.putUint16(0, 0);
+                }
+                else
+                {
+                    m_ZeroVelocityPixelValueSS.putSint16(1, 1);
+                }
+            }
+            else
+            {
+                DCMFG_ERROR("Cannot read Zero Velocity Pixel Value");
+            }
         }
-      }
-      else
-      {
-        DCMFG_ERROR("Cannot read Zero Velocity Pixel Value");
-      }
     }
-  }
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 // Writes single Frame Content Sequence into given item
 OFCondition FGImageDataType::write(DcmItem& item)
 {
-  DcmItem *seqItem = NULL;
-  OFCondition result = createNewFGSequence(item, DCM_ImageDataTypeSequence, 0, seqItem);
-  if (result.bad())
-    return result;
-
-  // --- write frame content macro attributes ---
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_DataType, "1", "1", "ImageDataTypeMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_AliasedDataType, "1", "1", "ImageDataTypeMacro");
-  if (!m_ZeroVelocityPixelValueSS.isEmpty())
-  {
-    DcmIODUtil::copyElementToDataset(result, *seqItem, m_ZeroVelocityPixelValueSS, "1", "1C", "ImageDataTypeMacro");
-  } else if (!m_ZeroVelocityPixelValueUS.isEmpty())
-  {
-    DcmIODUtil::copyElementToDataset(result, *seqItem, m_ZeroVelocityPixelValueUS, "1", "1C", "ImageDataTypeMacro");
-  }
-  // Zero Velocity Pixel Value is required in case Data Type is TISSUE_VELOCITY,
-  // FLOW_VELOCITY or DIRECTION_POWER.
-  else
-  {
-    OFString val;
-    m_DataType.getOFStringArray(val);
-    if ( (val == "TISSUE_VELOCITY") || (val == "FLOW_VELOCITY") ||  (val == "DIRECTION_POWER") )
+    DcmItem* seqItem   = NULL;
+    OFCondition result = createNewFGSequence(item, DCM_ImageDataTypeSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+
+    // --- write frame content macro attributes ---
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_DataType, "1", "1", "ImageDataTypeMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_AliasedDataType, "1", "1", "ImageDataTypeMacro");
+    if (!m_ZeroVelocityPixelValueSS.isEmpty())
     {
-      DCMFG_ERROR("Missing value for Zero Velocity Pixel Value (required if Data Type has" <<
-                  "the value TISSUE_VELOCITY, FLOW_VELOCITY or DIRECTION_POWER");
-      return FG_EC_InvalidData;
+        DcmIODUtil::copyElementToDataset(result, *seqItem, m_ZeroVelocityPixelValueSS, "1", "1C", "ImageDataTypeMacro");
+    }
+    else if (!m_ZeroVelocityPixelValueUS.isEmpty())
+    {
+        DcmIODUtil::copyElementToDataset(result, *seqItem, m_ZeroVelocityPixelValueUS, "1", "1C", "ImageDataTypeMacro");
+    }
+    // Zero Velocity Pixel Value is required in case Data Type is TISSUE_VELOCITY,
+    // FLOW_VELOCITY or DIRECTION_POWER.
+    else
+    {
+        OFString val;
+        m_DataType.getOFStringArray(val);
+        if ((val == "TISSUE_VELOCITY") || (val == "FLOW_VELOCITY") || (val == "DIRECTION_POWER"))
+        {
+            DCMFG_ERROR("Missing value for Zero Velocity Pixel Value (required if Data Type has"
+                        << "the value TISSUE_VELOCITY, FLOW_VELOCITY or DIRECTION_POWER");
+            return FG_EC_InvalidData;
+        }
     }
-  }
 
-  return result;
+    return result;
 }
 
-
 int FGImageDataType::compare(const FGBase& rhs) const
 {
-  int result = FGBase::compare(rhs);
-  if (result != 0)
-    return result;
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
+
+    const FGImageDataType* myRhs = OFstatic_cast(const FGImageDataType*, &rhs);
+    if (!myRhs)
+        return -1;
+
+    // Compare all elements
+    result = m_DataType.compare(myRhs->m_DataType);
+    if (result == 0)
+        result = m_AliasedDataType.compare(myRhs->m_AliasedDataType);
+    if (result == 0)
+        result = m_ZeroVelocityPixelValueSS.compare(myRhs->m_ZeroVelocityPixelValueSS);
+    if (result == 0)
+        result = m_ZeroVelocityPixelValueUS.compare(myRhs->m_ZeroVelocityPixelValueUS);
 
-  const FGImageDataType* myRhs = OFstatic_cast(const FGImageDataType*, &rhs);
-  if (!myRhs)
-    return -1;
-
-  // Compare all elements
-  result = m_DataType.compare(myRhs->m_DataType);
-  if (result == 0)
-    result = m_AliasedDataType.compare(myRhs->m_AliasedDataType);
-  if (result == 0)
-    result = m_ZeroVelocityPixelValueSS.compare(myRhs->m_ZeroVelocityPixelValueSS);
-  if (result == 0)
-    result = m_ZeroVelocityPixelValueUS.compare(myRhs->m_ZeroVelocityPixelValueUS);
-
-  return result;
+    return result;
 }
index 03b17c78c155161d72952c3b8520dc6f125ce4bc..81ce51a7f0cf7c31578e04d98ecf199f8850341d 100644 (file)
  */
 
 #include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmfg/fg.h"
+#include "dcmtk/dcmfg/fgfact.h" // for creating new functional groups
+#include "dcmtk/dcmfg/fginterface.h"
+#include "dcmtk/dcmiod/iodutil.h" // for static helpers
 #include "dcmtk/ofstd/ofmap.h"
 #include "dcmtk/ofstd/ofmem.h"
-#include "dcmtk/dcmiod/iodutil.h" // for static helpers
-#include "dcmtk/dcmfg/fginterface.h"
-#include "dcmtk/dcmfg/fg.h"
-#include "dcmtk/dcmfg/fgfact.h"   // for creating new functional groups
 
-
-FGInterface::FGInterface() :
-m_shared(),
-m_perFrame(),
-m_checkOnWrite(OFTrue)
+FGInterface::FGInterface()
+    : m_shared()
+    , m_perFrame()
+    , m_checkOnWrite(OFTrue)
 {
 }
 
-
 FGInterface::~FGInterface()
 {
-  clear();
+    clear();
 }
 
-
 void FGInterface::clear()
 {
-  // Clear per frame functional groups
-  while (m_perFrame.size() > 0)
-  {
-    OFMap<Uint32, FunctionalGroups*>::iterator it = m_perFrame.begin();
-    FunctionalGroups* fg = (*it).second;
-    m_perFrame.erase(it);
-    delete fg;
-  }
+    // Clear per frame functional groups
+    while (m_perFrame.size() > 0)
+    {
+        OFMap<Uint32, FunctionalGroups*>::iterator it = m_perFrame.begin();
+        FunctionalGroups* fg                          = (*it).second;
+        m_perFrame.erase(it);
+        delete fg;
+    }
 
-  // Clear shared functional groups
-  m_shared.clear();
+    // Clear shared functional groups
+    m_shared.clear();
 }
 
-
 size_t FGInterface::getNumberOfFrames()
 {
-  return m_perFrame.size();
+    return m_perFrame.size();
 }
 
-
 OFCondition FGInterface::addShared(const FGBase& group)
 {
-  DcmFGTypes::E_FGSharedType sharedType = group.getSharedType();
-  if ( sharedType == DcmFGTypes::EFGS_ONLYPERFRAME )
-  {
-    DCMFG_ERROR("Cannot add group as shared, per DICOM, group type " << DcmFGTypes::FGType2OFString(group.getType()) << " is always per-frame");
-    return FG_EC_CouldNotAddFG;
-  }
-
-  // Delete all per frame groups of this type
-  for (size_t count = 0; count < m_perFrame.size(); count++)
-  {
-    deletePerFrame(OFstatic_cast(Uint32, count), group.getType());
-  }
-
-  // Create copy for insertion
-  FGBase* copy = group.clone();
-  if (!copy)
-  {
-    return EC_MemoryExhausted;
-  }
-
-  // Insert shared one, replace old one if existing
-  OFCondition result = insertShared(copy, OFTrue /* replace */);
-  if (result.bad())
-  {
-    DCMFG_ERROR("Could not add shared group of type: " << DcmFGTypes::FGType2OFString(group.getType()));
-    delete copy;
-  }
-
-  return result;
-}
-
-
-OFCondition FGInterface::addPerFrame(const Uint32 frameNo,
-                                     const FGBase& group)
-{
-  OFCondition result = EC_Normal;
-  DcmFGTypes::E_FGSharedType sharedType = group.getSharedType();
-  if ( sharedType == DcmFGTypes::EFGS_ONLYSHARED)
-  {
-    DCMFG_ERROR("Cannot add group as per-frame, group type " << DcmFGTypes::FGType2OFString(group.getType()) << " is always shared");
-    return FG_EC_CouldNotAddFG;
-  }
-
-  // Check whether there is already a shared group of this type.
-  // If the content is equal to the given group, we re-use the shared one
-  FGBase* shared = getShared(group.getType());
-  // If there is a shared group
-  if ( shared )
-  {
-    // If shared has identical values as given group, nothing has to be done.
-    // Else if shared group with such type exists, but content differs,
-    // we must the make the existing shared FG "per-frame", i.e. distribute
-    // it to all frames, and add the given group for the given frame.
-    if ( (*shared).compare(group) != 0 )
-    {
-      // We need to unshare this group, i.e. distribute it to frames
-      DCMFG_DEBUG("Converting shared group of type " << DcmFGTypes::FGType2OFString(group.getType()) << " to per-frame, triggered by deviating per-frame insertion");
-      result = convertSharedToPerFrame(group.getType());
+    DcmFGTypes::E_FGSharedType sharedType = group.getSharedType();
+    if (sharedType == DcmFGTypes::EFGS_ONLYPERFRAME)
+    {
+        DCMFG_ERROR("Cannot add group as shared, per DICOM, group type " << DcmFGTypes::FGType2OFString(group.getType())
+                                                                         << " is always per-frame");
+        return FG_EC_CouldNotAddFG;
     }
-    else
+
+    // Delete all per frame groups of this type
+    for (size_t count = 0; count < m_perFrame.size(); count++)
     {
-      DCMFG_DEBUG("Re-using shared group instead of adding per-frame for frame " << frameNo << ", type " << DcmFGTypes::FGType2OFString(group.getType()));
-      return EC_Normal;
+        deletePerFrame(OFstatic_cast(Uint32, count), group.getType());
     }
-  }
 
-  if (result.good())
-  {
+    // Create copy for insertion
     FGBase* copy = group.clone();
     if (!copy)
     {
-      return EC_MemoryExhausted;
+        return EC_MemoryExhausted;
     }
-    result = insertPerFrame(frameNo, copy);
+
+    // Insert shared one, replace old one if existing
+    OFCondition result = insertShared(copy, OFTrue /* replace */);
     if (result.bad())
-      delete copy;
-  }
+    {
+        DCMFG_ERROR("Could not add shared group of type: " << DcmFGTypes::FGType2OFString(group.getType()));
+        delete copy;
+    }
 
-  return result;
+    return result;
 }
 
+OFCondition FGInterface::addPerFrame(const Uint32 frameNo, const FGBase& group)
+{
+    OFCondition result                    = EC_Normal;
+    DcmFGTypes::E_FGSharedType sharedType = group.getSharedType();
+    if (sharedType == DcmFGTypes::EFGS_ONLYSHARED)
+    {
+        DCMFG_ERROR("Cannot add group as per-frame, group type " << DcmFGTypes::FGType2OFString(group.getType())
+                                                                 << " is always shared");
+        return FG_EC_CouldNotAddFG;
+    }
+
+    // Check whether there is already a shared group of this type.
+    // If the content is equal to the given group, we re-use the shared one
+    FGBase* shared = getShared(group.getType());
+    // If there is a shared group
+    if (shared)
+    {
+        // If shared has identical values as given group, nothing has to be done.
+        // Else if shared group with such type exists, but content differs,
+        // we must the make the existing shared FG "per-frame", i.e. distribute
+        // it to all frames, and add the given group for the given frame.
+        if ((*shared).compare(group) != 0)
+        {
+            // We need to unshare this group, i.e. distribute it to frames
+            DCMFG_DEBUG("Converting shared group of type " << DcmFGTypes::FGType2OFString(
+                            group.getType()) << " to per-frame, triggered by deviating per-frame insertion");
+            result = convertSharedToPerFrame(group.getType());
+        }
+        else
+        {
+            DCMFG_DEBUG("Re-using shared group instead of adding per-frame for frame "
+                        << frameNo << ", type " << DcmFGTypes::FGType2OFString(group.getType()));
+            return EC_Normal;
+        }
+    }
+
+    if (result.good())
+    {
+        FGBase* copy = group.clone();
+        if (!copy)
+        {
+            return EC_MemoryExhausted;
+        }
+        result = insertPerFrame(frameNo, copy);
+        if (result.bad())
+            delete copy;
+    }
+
+    return result;
+}
 
 // Get specific functional group for a frame,
 // no matter whether it is stored per frame or shared
-FGBase* FGInterface::get(const Uint32 frameNo,
-                         const DcmFGTypes::E_FGType fgType)
+FGBase* FGInterface::get(const Uint32 frameNo, const DcmFGTypes::E_FGType fgType)
 {
-  OFBool helpShared; // throw-away variable
-  return get(frameNo, fgType, helpShared);
+    OFBool helpShared; // throw-away variable
+    return get(frameNo, fgType, helpShared);
 }
 
-
 const FunctionalGroups* FGInterface::getPerFrame(const Uint32 frameNo) const
 {
- if (frameNo > m_perFrame.size())
- {
-   return NULL;
- }
- else
- {
-   return (*(m_perFrame.find(frameNo))).second;
- }
   if (frameNo > m_perFrame.size())
   {
+        return NULL;
   }
   else
   {
+        return (*(m_perFrame.find(frameNo))).second;
   }
 }
 
-
 const FunctionalGroups* FGInterface::getShared() const
 {
-  return &m_shared;
+    return &m_shared;
 }
 
-
 // Read enhanced multi-frame information from DICOM item, usually DcmDataset
 OFCondition FGInterface::read(DcmItem& dataset)
 {
-  OFCondition result = EC_Normal;
+    OFCondition result = EC_Normal;
 
-  // clear any old values
-  clear();
+    // clear any old values
+    clear();
 
-  /* read shared functional groups */
-  if (result.good())
-  {
-    result = readSharedFG(dataset);
-  }
-
-  /* read per frame functional groups */
-  if (result.good())
-  {
-    result = readPerFrameFG(dataset);
-  }
+    /* read shared functional groups */
+    if (result.good())
+    {
+        result = readSharedFG(dataset);
+    }
 
-  return result;
+    /* read per frame functional groups */
+    if (result.good())
+    {
+        result = readPerFrameFG(dataset);
+    }
 
+    return result;
 }
 
-
 OFCondition FGInterface::readSharedFG(DcmItem& dataset)
 {
-  /* read shared functional groups */
-  DcmSequenceOfItems *shared = NULL;
-  OFCondition result = dataset.findAndGetSequence(DCM_SharedFunctionalGroupsSequence, shared);
-  if (result.bad())
-  {
-    DCMFG_ERROR("Could not find Shared Functional Group Sequence");
-    return FG_EC_NoSharedFG;
-  }
-
-  if (shared->card() > 1)
-  {
-    DCMFG_WARN("More than one item in Shared Functional Group Sequence, only considering the first one");
-  }
-  else if (shared->card() == 0)
-  {
-    DCMFG_WARN("No Item in Shared Functional Group Sequence but exactly one expected");
-    return FG_EC_NoSharedFG;
-  }
-
-  // get the only item of shared functional group sequence
-  DcmItem* sharedFGs = shared->getItem(0);
-  // read all functional groups from shared fg sequence item
-  result = readSingleFG(*sharedFGs, m_shared);
-
-  return result;
-}
-
-
+    /* read shared functional groups */
+    DcmSequenceOfItems* shared = NULL;
+    OFCondition result         = dataset.findAndGetSequence(DCM_SharedFunctionalGroupsSequence, shared);
+    if (result.bad())
+    {
+        DCMFG_ERROR("Could not find Shared Functional Group Sequence");
+        return FG_EC_NoSharedFG;
+    }
 
-OFCondition FGInterface::readPerFrameFG(DcmItem& dataset)
-{
-  /* read per-frame functional groups */
-  DcmSequenceOfItems *perFrame = NULL;
-  OFCondition result = dataset.findAndGetSequence(DCM_PerFrameFunctionalGroupsSequence, perFrame);
-  if (result.bad())
-  {
-    DCMFG_ERROR("Could not find Per-Frame Functional Group Sequence");
-    return FG_EC_NoPerFrameFG;
-  }
-
-  /* 1-n items required */
-  size_t numFrames = perFrame->card();
-  if (numFrames == 0)
-  {
-    DCMFG_WARN("No Item in Shared Functional Group Sequence but exactly one or more expected");
-    return FG_EC_NoPerFrameFG;
-  }
-
-  /* Read functional groups for each item (one per frame) */
-  DcmItem *oneFrameItem = OFstatic_cast(DcmItem*, perFrame->nextInContainer(NULL));
-  Uint32 count = 0;
-  while (oneFrameItem != NULL)
-  {
-    OFunique_ptr<FunctionalGroups> perFrameGroups(new FunctionalGroups());
-    if (!oneFrameItem)
-    {
-      DCMFG_ERROR("Could not get functional group item for frame #" << count << " (internal error)");
-    }
-    else if (!perFrameGroups.get())
-    {
-      DCMFG_ERROR("Could not create functional groups for frame #" << count << ": Memory exhausted?");
+    if (shared->card() > 1)
+    {
+        DCMFG_WARN("More than one item in Shared Functional Group Sequence, only considering the first one");
     }
-    else
+    else if (shared->card() == 0)
     {
-      result = readSingleFG(*oneFrameItem, *perFrameGroups);
-      if (result.good())
-      {
-        if ( !m_perFrame.insert( OFMake_pair(count, perFrameGroups.release()) ).second )
-        {
-          DCMFG_ERROR("Could not store functional groups for frame #" << count << " (internal error)");
-        }
-      }
-      else
-      {
-        DCMFG_ERROR("Could not read functional groups for frame #" << count << ": " << result.text());
-      }
-    }
-    oneFrameItem = OFstatic_cast(DcmItem*, perFrame->nextInContainer(oneFrameItem));
-    count++;
-  }
-  return EC_Normal; // for now we always return EC_Normal...
-}
+        DCMFG_WARN("No Item in Shared Functional Group Sequence but exactly one expected");
+        return FG_EC_NoSharedFG;
+    }
 
+    // get the only item of shared functional group sequence
+    DcmItem* sharedFGs = shared->getItem(0);
+    // read all functional groups from shared fg sequence item
+    result = readSingleFG(*sharedFGs, m_shared);
 
+    return result;
+}
 
-OFCondition FGInterface::readSingleFG(DcmItem& fgItem,
-                                      FunctionalGroups& groups)
+OFCondition FGInterface::readPerFrameFG(DcmItem& dataset)
 {
-  OFCondition result;
-  size_t card = fgItem.card();
-  OFString fgname;
-  for (size_t count = 0; count < card; count++)
-  {
-    DcmElement *elem = fgItem.getElement(OFstatic_cast(unsigned long, count));
-    // TODO: non-sequence elements are not explicitly forbidden here(?), we could store them and re-store them later
-    if (elem->getVR() != EVR_SQ)
+    /* read per-frame functional groups */
+    DcmSequenceOfItems* perFrame = NULL;
+    OFCondition result           = dataset.findAndGetSequence(DCM_PerFrameFunctionalGroupsSequence, perFrame);
+    if (result.bad())
     {
-      DCMFG_WARN("Found non-sequence element in functional group sequence item (ignored): " << elem->getTag());
+        DCMFG_ERROR("Could not find Per-Frame Functional Group Sequence");
+        return FG_EC_NoPerFrameFG;
     }
-    else
+
+    /* 1-n items required */
+    size_t numFrames = perFrame->card();
+    if (numFrames == 0)
     {
-      FGBase *fg = FGFactory::instance().create(elem->getTag());
-      if (fg != NULL)
-      {
-        OFStringStream stream;
-        stream << DcmFGTypes::tagKey2FGString(elem->getTag()) << " " << elem->getTag();
-        OFSTRINGSTREAM_GETSTR(stream,tmpstr)
-        fgname = tmpstr;
-        OFSTRINGSTREAM_FREESTR(tmpstr)
-        result = fg->read(fgItem);
-        if (result.bad())
+        DCMFG_WARN("No Item in Shared Functional Group Sequence but exactly one or more expected");
+        return FG_EC_NoPerFrameFG;
+    }
+
+    /* Read functional groups for each item (one per frame) */
+    DcmItem* oneFrameItem = OFstatic_cast(DcmItem*, perFrame->nextInContainer(NULL));
+    Uint32 count          = 0;
+    while (oneFrameItem != NULL)
+    {
+        OFunique_ptr<FunctionalGroups> perFrameGroups(new FunctionalGroups());
+        if (!oneFrameItem)
         {
-          DCMFG_WARN("Cannot read functional group: " << fgname << " (ignored)");
+            DCMFG_ERROR("Could not get functional group item for frame #" << count << " (internal error)");
         }
-        // we also accept groups while reading which could instantiated but not could not be read
-        result = groups.insert(fg, OFTrue);
-        if (result.good())
+        else if (!perFrameGroups.get())
         {
-          DCMFG_DEBUG("Inserted functional group: " << fgname );
+            DCMFG_ERROR("Could not create functional groups for frame #" << count << ": Memory exhausted?");
         }
         else
         {
-          DCMFG_ERROR("Could not insert functional group: " << fgname << " (internal error)");
-          delete fg;
+            result = readSingleFG(*oneFrameItem, *perFrameGroups);
+            if (result.good())
+            {
+                if (!m_perFrame.insert(OFMake_pair(count, perFrameGroups.release())).second)
+                {
+                    DCMFG_ERROR("Could not store functional groups for frame #" << count << " (internal error)");
+                }
+            }
+            else
+            {
+                DCMFG_ERROR("Could not read functional groups for frame #" << count << ": " << result.text());
+            }
         }
-      }
-      else
-      {
-        DCMFG_WARN("Cannot understand functional group for sequence tag: " << elem->getTag());
-      }
-    }
-  }
-  return EC_Normal; // for now we always return EC_Normal...
+        oneFrameItem = OFstatic_cast(DcmItem*, perFrame->nextInContainer(oneFrameItem));
+        count++;
+    }
+    return EC_Normal; // for now we always return EC_Normal...
 }
 
+OFCondition FGInterface::readSingleFG(DcmItem& fgItem, FunctionalGroups& groups)
+{
+    OFCondition result;
+    size_t card = fgItem.card();
+    OFString fgname;
+    for (size_t count = 0; count < card; count++)
+    {
+        DcmElement* elem = fgItem.getElement(OFstatic_cast(unsigned long, count));
+        // TODO: non-sequence elements are not explicitly forbidden here(?), we could store them and re-store them later
+        if (elem->getVR() != EVR_SQ)
+        {
+            DCMFG_WARN("Found non-sequence element in functional group sequence item (ignored): " << elem->getTag());
+        }
+        else
+        {
+            FGBase* fg = FGFactory::instance().create(elem->getTag());
+            if (fg != NULL)
+            {
+                OFStringStream stream;
+                stream << DcmFGTypes::tagKey2FGString(elem->getTag()) << " " << elem->getTag();
+                OFSTRINGSTREAM_GETSTR(stream, tmpstr)
+                fgname = tmpstr;
+                OFSTRINGSTREAM_FREESTR(tmpstr)
+                result = fg->read(fgItem);
+                if (result.bad())
+                {
+                    DCMFG_WARN("Cannot read functional group: " << fgname << " (ignored)");
+                }
+                // we also accept groups while reading which could instantiated but not could not be read
+                result = groups.insert(fg, OFTrue);
+                if (result.good())
+                {
+                    DCMFG_DEBUG("Inserted functional group: " << fgname);
+                }
+                else
+                {
+                    DCMFG_ERROR("Could not insert functional group: " << fgname << " (internal error)");
+                    delete fg;
+                }
+            }
+            else
+            {
+                DCMFG_WARN("Cannot understand functional group for sequence tag: " << elem->getTag());
+            }
+        }
+    }
+    return EC_Normal; // for now we always return EC_Normal...
+}
 
 // Write enhanced multi-frame information to DICOM item, usually DcmDataset
 OFCondition FGInterface::write(DcmItem& dataset)
 {
-  //Check data integrity of functional group macros */
-  if (m_checkOnWrite)
-  {
-    if ( !check() )
-      return FG_EC_CouldNotWriteFG;
-  }
+    // Check data integrity of functional group macros */
+    if (m_checkOnWrite)
+    {
+        if (!check())
+            return FG_EC_CouldNotWriteFG;
+    }
 
-  // Write shared functional Groups
-  OFCondition result = writeSharedFG(dataset);
+    // Write shared functional Groups
+    OFCondition result = writeSharedFG(dataset);
 
-  // Write per frame functional groups
-  if ( result.good() ) result = writePerFrameFG(dataset);
+    // Write per frame functional groups
+    if (result.good())
+        result = writePerFrameFG(dataset);
 
-  return result;
+    return result;
 }
 
-
 FGBase* FGInterface::getShared(const DcmFGTypes::E_FGType fgType)
 {
-  return m_shared.find(fgType);
+    return m_shared.find(fgType);
 }
 
-
-OFCondition FGInterface::insertShared(FGBase* group,
-                                      const OFBool replaceExisting)
+OFCondition FGInterface::insertShared(FGBase* group, const OFBool replaceExisting)
 {
-  return m_shared.insert(group, replaceExisting);
+    return m_shared.insert(group, replaceExisting);
 }
 
-
-FGBase* FGInterface::getPerFrame(const Uint32 frameNo,
-                                 const DcmFGTypes::E_FGType fgType)
+FGBase* FGInterface::getPerFrame(const Uint32 frameNo, const DcmFGTypes::E_FGType fgType)
 {
-  FGBase* group = NULL;
-  OFMap<Uint32, FunctionalGroups*>::iterator it = m_perFrame.find(frameNo);
-  if ( it != m_perFrame.end() )
-  {
-    FunctionalGroups* perFrameGroups = (*it).second;
-    group = perFrameGroups->find(fgType);
-  }
-
-  return group;
-}
+    FGBase* group                                 = NULL;
+    OFMap<Uint32, FunctionalGroups*>::iterator it = m_perFrame.find(frameNo);
+    if (it != m_perFrame.end())
+    {
+        FunctionalGroups* perFrameGroups = (*it).second;
+        group                            = perFrameGroups->find(fgType);
+    }
 
+    return group;
+}
 
 OFBool FGInterface::deleteShared(const DcmFGTypes::E_FGType fgType)
 {
-  FGBase* group = m_shared.find(fgType);
-  if (group)
-  {
-    delete m_shared.remove(fgType);
-    return OFTrue;
-  }
-  return OFFalse;
+    FGBase* group = m_shared.find(fgType);
+    if (group)
+    {
+        delete m_shared.remove(fgType);
+        return OFTrue;
+    }
+    return OFFalse;
 }
 
-
-
-OFBool FGInterface::deletePerFrame(const Uint32 frameNo,
-                                   const DcmFGTypes::E_FGType fgType)
+OFBool FGInterface::deletePerFrame(const Uint32 frameNo, const DcmFGTypes::E_FGType fgType)
 {
-  OFMap<Uint32, FunctionalGroups*>::iterator it = m_perFrame.find(frameNo);
-  if (it != m_perFrame.end())
-  {
-    if ( (*it).second )
-    {
-      FGBase *remove = (*it).second->remove(fgType);
-      if (remove)
-      {
-        DCMFG_DEBUG("Deleting FG for frame " << frameNo << ", type: " << DcmFGTypes::FGType2OFString(fgType));
-        delete remove;
-        remove = NULL;
-        return OFTrue;
-      }
+    OFMap<Uint32, FunctionalGroups*>::iterator it = m_perFrame.find(frameNo);
+    if (it != m_perFrame.end())
+    {
+        if ((*it).second)
+        {
+            FGBase* remove = (*it).second->remove(fgType);
+            if (remove)
+            {
+                DCMFG_DEBUG("Deleting FG for frame " << frameNo << ", type: " << DcmFGTypes::FGType2OFString(fgType));
+                delete remove;
+                remove = NULL;
+                return OFTrue;
+            }
+        }
     }
-  }
-  return OFFalse;
+    return OFFalse;
 }
 
-
 size_t FGInterface::deletePerFrame(const DcmFGTypes::E_FGType fgType)
 {
-  size_t numDeleted = 0;
-  const size_t numFrames = m_perFrame.size();
-  for (size_t frameNo = 0; frameNo < numFrames; frameNo++)
-  {
-    if (deletePerFrame(OFstatic_cast(Uint32, frameNo), fgType))
+    size_t numDeleted      = 0;
+    const size_t numFrames = m_perFrame.size();
+    for (size_t frameNo = 0; frameNo < numFrames; frameNo++)
     {
-      numDeleted++;
+        if (deletePerFrame(OFstatic_cast(Uint32, frameNo), fgType))
+        {
+            numDeleted++;
+        }
     }
-  }
-  return numDeleted;
+    return numDeleted;
 }
 
-
 size_t FGInterface::deleteFrame(const Uint32 frameNo)
 {
-  OFMap<Uint32, FunctionalGroups*>::iterator it = m_perFrame.find(frameNo);
-  if (it != m_perFrame.end())
-  {
-    if ( (*it).second )
-    {
-      FunctionalGroups::iterator fg = (*it).second->begin();
-      while (fg != (*it).second->end())
-      {
-        delete (*fg).second;
-        fg++;
-      }
-    }
-    m_perFrame.erase(it);
-  }
-  return OFFalse;
+    OFMap<Uint32, FunctionalGroups*>::iterator it = m_perFrame.find(frameNo);
+    if (it != m_perFrame.end())
+    {
+        if ((*it).second)
+        {
+            FunctionalGroups::iterator fg = (*it).second->begin();
+            while (fg != (*it).second->end())
+            {
+                delete (*fg).second;
+                fg++;
+            }
+        }
+        m_perFrame.erase(it);
+    }
+    return OFFalse;
 }
 
-
 void FGInterface::setCheckOnWrite(const OFBool doCheck)
 {
-  m_checkOnWrite = doCheck;
+    m_checkOnWrite = doCheck;
 }
 
-
 OFBool FGInterface::getCheckOnWrite()
 {
-  return m_checkOnWrite;
+    return m_checkOnWrite;
 }
 
-
 FunctionalGroups* FGInterface::getOrCreatePerFrameGroups(const Uint32 frameNo)
 {
-  OFMap<Uint32, FunctionalGroups*>::iterator it = m_perFrame.find(frameNo);
-  if (it != m_perFrame.end())
-    return (*it).second;
-
-  FunctionalGroups *fg = new FunctionalGroups();
-  if (fg != NULL)
-  {
-    if ( !(m_perFrame.insert(OFMake_pair(frameNo, fg))).second )
-    {
-      DCMFG_ERROR("Could not insert Per-frame Functional Groups for frame " << frameNo << ": " << "Internal error");
-      delete fg;
-      fg = NULL;
-    }
-  }
-  else
-  {
-    DCMFG_ERROR("Could not create Per-frame Functional Groups for frame " << frameNo << ": " << "Memory exhausted");
-  }
-
-  return fg;
-}
+    OFMap<Uint32, FunctionalGroups*>::iterator it = m_perFrame.find(frameNo);
+    if (it != m_perFrame.end())
+        return (*it).second;
 
+    FunctionalGroups* fg = new FunctionalGroups();
+    if (fg != NULL)
+    {
+        if (!(m_perFrame.insert(OFMake_pair(frameNo, fg))).second)
+        {
+            DCMFG_ERROR("Could not insert Per-frame Functional Groups for frame " << frameNo << ": "
+                                                                                  << "Internal error");
+            delete fg;
+            fg = NULL;
+        }
+    }
+    else
+    {
+        DCMFG_ERROR("Could not create Per-frame Functional Groups for frame " << frameNo << ": "
+                                                                              << "Memory exhausted");
+    }
+
+    return fg;
+}
 
 OFCondition FGInterface::writePerFrameFG(DcmItem& dataset)
 {
-  DCMFG_DEBUG("Writing per-frame functional groups");
-  OFCondition result = dataset.insertEmptyElement(DCM_PerFrameFunctionalGroupsSequence, OFTrue); // start with empty sequence
-  if (result.bad())
-  {
-    DCMFG_ERROR("Could not create Per-frame Functional Groups Sequence");
-    return result;
-  }
-
-  /* Iterate over frames */
-  OFMap<Uint32, FunctionalGroups*>::iterator it = m_perFrame.begin();
-  size_t numFrames = m_perFrame.size();
-  for ( size_t count = 0; (count < numFrames)  && result.good(); count++)
-  {
-    DcmItem* perFrameItem = NULL;
-    result = dataset.findOrCreateSequenceItem(DCM_PerFrameFunctionalGroupsSequence, perFrameItem, OFstatic_cast(long, count));
-    if (result.good())
+    DCMFG_DEBUG("Writing per-frame functional groups");
+    OFCondition result
+        = dataset.insertEmptyElement(DCM_PerFrameFunctionalGroupsSequence, OFTrue); // start with empty sequence
+    if (result.bad())
     {
-      /* Iterate over groups for each frame */
-      FunctionalGroups::iterator groupIt = (*it).second->begin();
-      while ( result.good() && (groupIt != (*it).second->end()) )
-      {
-        DCMFG_DEBUG("Writing per-frame group: " << DcmFGTypes::FGType2OFString((*groupIt).second->getType()) << " for frame #" << count);
-        result = (*groupIt).second->write(*perFrameItem);
-        groupIt++;
-      }
+        DCMFG_ERROR("Could not create Per-frame Functional Groups Sequence");
+        return result;
     }
-    else
+
+    /* Iterate over frames */
+    OFMap<Uint32, FunctionalGroups*>::iterator it = m_perFrame.begin();
+    size_t numFrames                              = m_perFrame.size();
+    for (size_t count = 0; (count < numFrames) && result.good(); count++)
     {
-      DCMFG_ERROR("Cannot create item in Per-frame Functional Groups Sequence");
+        DcmItem* perFrameItem = NULL;
+        result                = dataset.findOrCreateSequenceItem(
+            DCM_PerFrameFunctionalGroupsSequence, perFrameItem, OFstatic_cast(long, count));
+        if (result.good())
+        {
+            /* Iterate over groups for each frame */
+            FunctionalGroups::iterator groupIt = (*it).second->begin();
+            while (result.good() && (groupIt != (*it).second->end()))
+            {
+                DCMFG_DEBUG("Writing per-frame group: " << DcmFGTypes::FGType2OFString((*groupIt).second->getType())
+                                                        << " for frame #" << count);
+                result = (*groupIt).second->write(*perFrameItem);
+                groupIt++;
+            }
+        }
+        else
+        {
+            DCMFG_ERROR("Cannot create item in Per-frame Functional Groups Sequence");
+        }
+        it++;
     }
-    it++;
-  }
-  return result;
+    return result;
 }
 
-
 OFCondition FGInterface::writeSharedFG(DcmItem& dataset)
 {
-  DCMFG_DEBUG("Writing shared functional groups");
-  OFCondition result = dataset.insertEmptyElement(DCM_SharedFunctionalGroupsSequence, OFTrue); // start with empty sequence
-  DcmItem *sharedFGItem = NULL;
-  if (result.good())
-  {
-    result = dataset.findOrCreateSequenceItem(DCM_SharedFunctionalGroupsSequence, sharedFGItem, 0);
-  }
-  if (result.bad())
-  {
-    DCMFG_ERROR("Could not create Shared Functional Groups Sequence with single item");
+    DCMFG_DEBUG("Writing shared functional groups");
+    OFCondition result
+        = dataset.insertEmptyElement(DCM_SharedFunctionalGroupsSequence, OFTrue); // start with empty sequence
+    DcmItem* sharedFGItem = NULL;
+    if (result.good())
+    {
+        result = dataset.findOrCreateSequenceItem(DCM_SharedFunctionalGroupsSequence, sharedFGItem, 0);
+    }
+    if (result.bad())
+    {
+        DCMFG_ERROR("Could not create Shared Functional Groups Sequence with single item");
+        return result;
+    }
+
+    FunctionalGroups::iterator it  = m_shared.begin();
+    FunctionalGroups::iterator end = m_shared.end();
+    while ((it != end) && result.good())
+    {
+        DCMFG_DEBUG("Writing shared group: " << DcmFGTypes::FGType2OFString((*it).second->getType()));
+        result = (*it).second->write(*sharedFGItem);
+        it++;
+    }
     return result;
-  }
-
-  FunctionalGroups::iterator it = m_shared.begin();
-  FunctionalGroups::iterator end = m_shared.end();
-  while ( (it != end) && result.good() )
-  {
-    DCMFG_DEBUG("Writing shared group: " << DcmFGTypes::FGType2OFString((*it).second->getType()));
-    result = (*it).second->write(*sharedFGItem);
-    it++;
-  }
-  return result;
 }
 
-
-OFCondition FGInterface::insertPerFrame(const Uint32 frameNo,
-                                        FGBase* group,
-                                        const OFBool replaceExisting)
+OFCondition FGInterface::insertPerFrame(const Uint32 frameNo, FGBase* group, const OFBool replaceExisting)
 {
-  if (group == NULL)
-    return EC_IllegalParameter;
+    if (group == NULL)
+        return EC_IllegalParameter;
 
-  OFCondition result = EC_Normal;
-  FGBase* existing = getPerFrame(frameNo, group->getType());
-  if (existing)
-  {
-    if (replaceExisting)
+    OFCondition result = EC_Normal;
+    FGBase* existing   = getPerFrame(frameNo, group->getType());
+    if (existing)
     {
-      DCMFG_DEBUG("Replacing per-frame FG for frame: " << frameNo << ", type: " << DcmFGTypes::FGType2OFString(group->getType()));
-      deletePerFrame(frameNo, group->getType());
+        if (replaceExisting)
+        {
+            DCMFG_DEBUG("Replacing per-frame FG for frame: " << frameNo << ", type: "
+                                                             << DcmFGTypes::FGType2OFString(group->getType()));
+            deletePerFrame(frameNo, group->getType());
+        }
+        else
+        {
+            result = FG_EC_DoubledFG;
+        }
     }
-    else
+
+    // Insert per-frame functional group
+    if (result.good())
     {
-      result = FG_EC_DoubledFG;
+        FunctionalGroups* perFrameGroups = getOrCreatePerFrameGroups(frameNo);
+        if (perFrameGroups != NULL)
+        {
+            result = perFrameGroups->insert(group, replaceExisting);
+        }
+        else
+        {
+            result = FG_EC_CouldNotInsertFG;
+        }
     }
-  }
+    return result;
+}
 
-  // Insert per-frame functional group
-  if (result.good())
-  {
-    FunctionalGroups* perFrameGroups = getOrCreatePerFrameGroups(frameNo);
-    if (perFrameGroups != NULL)
+OFCondition FGInterface::convertSharedToPerFrame(const DcmFGTypes::E_FGType fgType)
+{
+    FGBase* shared = m_shared.remove(fgType);
+    if (!shared)
     {
-      result = perFrameGroups->insert(group, replaceExisting);
+        return FG_EC_NoSuchGroup;
     }
-    else
+
+    OFCondition result;
+    size_t numFrames = m_perFrame.size();
+    // Walk over all existing frames and copy "old" shared group to them
+    size_t count = 0;
+    for (count = 0; result.good() && (count < numFrames); count++)
     {
-      result = FG_EC_CouldNotInsertFG;
+        FGBase* clone = shared->clone();
+        if (!clone)
+        {
+            result = EC_MemoryExhausted;
+        }
+        else
+        {
+            result = insertPerFrame(OFstatic_cast(Uint32, count), clone, OFTrue /* replace existing */);
+            if (result.bad())
+            {
+                delete clone;
+            }
+        }
     }
-  }
-  return result;
+    return result;
 }
 
-
-OFCondition FGInterface::convertSharedToPerFrame(const DcmFGTypes::E_FGType fgType)
+FGBase* FGInterface::get(const Uint32 frameNo, const DcmFGTypes::E_FGType fgType, OFBool& isPerFrame)
 {
-  FGBase* shared = m_shared.remove(fgType);
-  if (!shared)
-  {
-    return FG_EC_NoSuchGroup;
-  }
-
-  OFCondition result;
-  size_t numFrames = m_perFrame.size();
-  // Walk over all existing frames and copy "old" shared group to them
-  size_t count = 0;
-  for (count = 0; result.good() && (count < numFrames); count++)
-  {
-    FGBase* clone = shared->clone();
-    if (!clone)
-    {
-      result = EC_MemoryExhausted;
+    FGBase* group = m_shared.find(fgType);
+    if (!group)
+    {
+        group      = getPerFrame(frameNo, fgType);
+        isPerFrame = OFTrue;
     }
     else
     {
-      result = insertPerFrame(OFstatic_cast(Uint32, count), clone, OFTrue /* replace existing */);
-      if (result.bad())
-      {
-        delete clone;
-      }
+        isPerFrame = OFFalse;
     }
-  }
-  return result ;
-}
 
-
-FGBase* FGInterface::get(const Uint32 frameNo,
-                         const DcmFGTypes::E_FGType fgType,
-                         OFBool& isPerFrame)
-{
-  FGBase *group = m_shared.find(fgType);
-  if ( !group )
-  {
-    group = getPerFrame(frameNo, fgType);
-    isPerFrame = OFTrue;
-  }
-  else
-  {
-    isPerFrame = OFFalse;
-  }
-
-  return group;
+    return group;
 }
 
-
 OFBool FGInterface::check()
 {
-  size_t numFrames = m_perFrame.size();
-  DCMFG_DEBUG("Checking functional group structure for " << numFrames << " frames");
-  size_t numErrors = 0;
-  for (size_t frameCount = 0; frameCount < numFrames; frameCount++)
-  {
-    DCMFG_TRACE("Checking frame " << frameCount << "...");
-    // Every frame requires the FrameContent functional group, check "en passant"
-    OFBool foundFrameContent = OFFalse;
-    OFMap<Uint32, FunctionalGroups*>::iterator frameFG = m_perFrame.begin();
-    OFMap<Uint32, FunctionalGroups*>::iterator end = m_perFrame.end();
-    while (frameFG != end)
-    {
-      FunctionalGroups::iterator group = (*frameFG).second->begin();
-      FunctionalGroups::iterator groupEnd = (*frameFG).second->end();
-      while (group != groupEnd)
-      {
-        // Check that per-frame group is not a shared group at the same time
-        DcmFGTypes::E_FGType groupType = group->second->getType();
-        if ( (groupType != DcmFGTypes::EFG_UNDEFINED) &&
-          (groupType != DcmFGTypes::EFG_UNKNOWN) )
+    size_t numFrames = m_perFrame.size();
+    DCMFG_DEBUG("Checking functional group structure for " << numFrames << " frames");
+    size_t numErrors = 0;
+    for (size_t frameCount = 0; frameCount < numFrames; frameCount++)
+    {
+        DCMFG_TRACE("Checking frame " << frameCount << "...");
+        // Every frame requires the FrameContent functional group, check "en passant"
+        OFBool foundFrameContent                           = OFFalse;
+        OFMap<Uint32, FunctionalGroups*>::iterator frameFG = m_perFrame.begin();
+        OFMap<Uint32, FunctionalGroups*>::iterator end     = m_perFrame.end();
+        while (frameFG != end)
         {
-          if (m_shared.find(groupType) != NULL)
-          {
-            DCMFG_ERROR("Functional group of type " << DcmFGTypes::FGType2OFString(groupType) << " is shared AND per-frame for frame " << frameCount);
-            numErrors++;
-          }
-          if (groupType == DcmFGTypes::EFG_FRAMECONTENT)
-            foundFrameContent = OFTrue;
+            FunctionalGroups::iterator group    = (*frameFG).second->begin();
+            FunctionalGroups::iterator groupEnd = (*frameFG).second->end();
+            while (group != groupEnd)
+            {
+                // Check that per-frame group is not a shared group at the same time
+                DcmFGTypes::E_FGType groupType = group->second->getType();
+                if ((groupType != DcmFGTypes::EFG_UNDEFINED) && (groupType != DcmFGTypes::EFG_UNKNOWN))
+                {
+                    if (m_shared.find(groupType) != NULL)
+                    {
+                        DCMFG_ERROR("Functional group of type " << DcmFGTypes::FGType2OFString(groupType)
+                                                                << " is shared AND per-frame for frame " << frameCount);
+                        numErrors++;
+                    }
+                    if (groupType == DcmFGTypes::EFG_FRAMECONTENT)
+                        foundFrameContent = OFTrue;
+                }
+                // Check if "per-frame" is allowed for this group;
+                if (group->second->getSharedType() == DcmFGTypes::EFGS_ONLYSHARED)
+                {
+                    DCMFG_ERROR("Functional group of type " << DcmFGTypes::FGType2OFString(groupType)
+                                                            << " can never be per-frame, but found for frame "
+                                                            << frameCount);
+                    numErrors++;
+                }
+                group++;
+            }
+            frameFG++;
         }
-        // Check if "per-frame" is allowed for this group;
-        if (group->second->getSharedType() == DcmFGTypes::EFGS_ONLYSHARED)
+        if (!foundFrameContent)
         {
-          DCMFG_ERROR("Functional group of type " << DcmFGTypes::FGType2OFString(groupType) << " can never be per-frame, but found for frame " << frameCount);
-          numErrors++;
+            DCMFG_ERROR("Frame Content Functional group missing for frame #" << frameCount);
+            numErrors++;
         }
-        group++;
-      }
-      frameFG++;
     }
-    if (!foundFrameContent)
-    {
-      DCMFG_ERROR("Frame Content Functional group missing for frame #" << frameCount);
-      numErrors++;
-    }
-  }
 
-  // Check whether shared groups contain FGs that are only permitted per-frame
-  FunctionalGroups::iterator it = m_shared.begin();
-  FunctionalGroups::iterator end = m_shared.end();
-  while (it != end)
-  {
-    if ( (*it).second->getSharedType() == DcmFGTypes::EFGS_ONLYPERFRAME )
+    // Check whether shared groups contain FGs that are only permitted per-frame
+    FunctionalGroups::iterator it  = m_shared.begin();
+    FunctionalGroups::iterator end = m_shared.end();
+    while (it != end)
     {
-      DCMFG_ERROR("Functional group of type " << DcmFGTypes::FGType2OFString((*it).second->getType()) << " used as shared functional group but must be per-frame");
-      numErrors++;
+        if ((*it).second->getSharedType() == DcmFGTypes::EFGS_ONLYPERFRAME)
+        {
+            DCMFG_ERROR("Functional group of type " << DcmFGTypes::FGType2OFString((*it).second->getType())
+                                                    << " used as shared functional group but must be per-frame");
+            numErrors++;
+        }
+        it++;
     }
-    it++;
-  }
 
-  if (numErrors > 0)
-    return OFFalse;
+    if (numErrors > 0)
+        return OFFalse;
 
-  return OFTrue;
+    return OFTrue;
 }
diff --git a/dcmfg/libsrc/fgirradiationeventid.cc b/dcmfg/libsrc/fgirradiationeventid.cc
new file mode 100644 (file)
index 0000000..5490e1a
--- /dev/null
@@ -0,0 +1,122 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Class for managing the Irradiation Event Identification Functional Group
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgirradiationeventid.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/dcmiod/iodutil.h"
+
+// Constructor
+FGIrradiationEventIdentification::FGIrradiationEventIdentification()
+    : FGBase(DcmFGTypes::EFG_IRRADIATIONEVENTIDENT)
+    , m_IrraditionEventUID(DCM_IrradiationEventUID)
+{
+}
+
+FGIrradiationEventIdentification::~FGIrradiationEventIdentification()
+{
+    // nothing to do
+}
+
+FGBase* FGIrradiationEventIdentification::clone() const
+{
+    FGIrradiationEventIdentification* copy = new FGIrradiationEventIdentification();
+    if (copy)
+    {
+        copy->m_IrraditionEventUID = this->m_IrraditionEventUID;
+    }
+    return copy;
+}
+
+void FGIrradiationEventIdentification::clearData()
+{
+    m_IrraditionEventUID.clear();
+}
+
+OFCondition FGIrradiationEventIdentification::check() const
+{
+    // Maybe add checks later
+    return EC_Normal;
+}
+
+// Read Irradiation Event Identification Sequence from given item
+OFCondition FGIrradiationEventIdentification::read(DcmItem& item)
+{
+    clearData();
+
+    DcmItem* seqItem   = NULL;
+    OFCondition result = getItemFromFGSequence(item, DCM_IrradiationEventIdentificationSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+
+    DcmIODUtil::getAndCheckElementFromDataset(
+        *seqItem, m_IrraditionEventUID, "1", "", "IrradiationEventIdentificationMacro");
+
+    return EC_Normal;
+}
+
+// Writes single Irradiation Event Identification Sequence into given item
+OFCondition FGIrradiationEventIdentification::write(DcmItem& item)
+{
+    DcmItem* seqItem   = NULL;
+    OFCondition result = createNewFGSequence(item, DCM_IrradiationEventIdentificationSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+
+    // --- write Irradiation Event Identification Sequence attributes ---
+    DcmIODUtil::copyElementToDataset(
+        result, *seqItem, m_IrraditionEventUID, "1", "1", "IrradiationEventIdentificationMacro");
+    return result;
+}
+
+int FGIrradiationEventIdentification::compare(const FGBase& rhs) const
+{
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
+
+    const FGIrradiationEventIdentification* myRhs = OFstatic_cast(const FGIrradiationEventIdentification*, &rhs);
+    if (!myRhs)
+        return -1;
+
+    // Compare all elements
+    result = m_IrraditionEventUID.compare(myRhs->m_IrraditionEventUID);
+    return result;
+}
+
+// --- get() functionality ---
+
+OFCondition FGIrradiationEventIdentification::getIrradiationEventUID(OFString& value, const long pos)
+{
+    return DcmIODUtil::getStringValueFromElement(m_IrraditionEventUID, value, pos);
+}
+
+// --- set() functionality ---
+
+OFCondition FGIrradiationEventIdentification::setIrradiationEventUID(const OFString& value, const OFBool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_IrraditionEventUID.putOFStringArray(value);
+    return result;
+}
index d3956057c37438e9ff797f35398629e781b98c65..66591790149ac032ba61b922d53f2ce4291af987 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016-2018, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  */
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcdeftag.h"
-#include "dcmtk/dcmiod/iodutil.h"
 #include "dcmtk/dcmfg/fgparametricmapframetype.h"
+#include "dcmtk/dcmiod/iodutil.h"
 
 FGParametricMapFrameType::FGParametricMapFrameType()
-: FGBase(DcmFGTypes::EFG_PARAMETRICMAPFRAMETYPE)
-, m_FrameType(DCM_FrameType)
+    : FGBase(DcmFGTypes::EFG_PARAMETRICMAPFRAMETYPE)
+    , m_FrameType(DCM_FrameType)
 {
-
 }
 
 FGParametricMapFrameType::~FGParametricMapFrameType()
 {
-
 }
 
 void FGParametricMapFrameType::clearData()
 {
-  m_FrameType.clear();
+    m_FrameType.clear();
 }
 
 FGBase* FGParametricMapFrameType::clone() const
 {
-  if(FGParametricMapFrameType* copy = new FGParametricMapFrameType)
-  {
-    copy->m_FrameType = m_FrameType;
-    return copy;
-  }
-  return OFnullptr;
+    if (FGParametricMapFrameType* copy = new FGParametricMapFrameType)
+    {
+        copy->m_FrameType = m_FrameType;
+        return copy;
+    }
+    return OFnullptr;
 }
 
 OFCondition FGParametricMapFrameType::read(DcmItem& item)
 {
-  clearData();
+    clearData();
 
-  DcmItem* seqItem;
-  OFCondition result;
+    DcmItem* seqItem;
+    OFCondition result;
 
-  seqItem = OFnullptr;
-  result = getItemFromFGSequence(item, DCM_ParametricMapFrameTypeSequence, 0, seqItem);
-  if(result.bad())
-    return result;
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FrameType, "4", "1", "Parametric Map Frame Type");
+    seqItem = OFnullptr;
+    result  = getItemFromFGSequence(item, DCM_ParametricMapFrameTypeSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FrameType, "4", "1", "Parametric Map Frame Type");
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 OFCondition FGParametricMapFrameType::write(DcmItem& item)
 {
-  OFCondition result = check();
-  if (result.good())
-  {
-    DcmItem* seqItem;
-    seqItem = OFnullptr;
-    result = createNewFGSequence(item, DCM_ParametricMapFrameTypeSequence, 0, seqItem);
-    if(result.good())
+    OFCondition result = check();
+    if (result.good())
     {
-      DcmIODUtil::copyElementToDataset(result, *seqItem, m_FrameType, "4", "1", "Parametric Map Frame Type");
+        DcmItem* seqItem;
+        seqItem = OFnullptr;
+        result  = createNewFGSequence(item, DCM_ParametricMapFrameTypeSequence, 0, seqItem);
+        if (result.good())
+        {
+            DcmIODUtil::copyElementToDataset(result, *seqItem, m_FrameType, "4", "1", "Parametric Map Frame Type");
+        }
     }
-  }
-  return result;
+    return result;
 }
 
-
 int FGParametricMapFrameType::compare(const FGBase& rhs) const
 {
-  int result = FGBase::compare(rhs);
-  if(result == 0)
-  {
-    const FGParametricMapFrameType* myRhs = OFstatic_cast(const FGParametricMapFrameType*, &rhs);
-    if (!myRhs)
-        return -1;
-
-    // Compare all elements
-    result = m_FrameType.compare(myRhs->m_FrameType);
-  }
-
-  return result;
-}
+    int result = FGBase::compare(rhs);
+    if (result == 0)
+    {
+        const FGParametricMapFrameType* myRhs = OFstatic_cast(const FGParametricMapFrameType*, &rhs);
+        if (!myRhs)
+            return -1;
+
+        // Compare all elements
+        result = m_FrameType.compare(myRhs->m_FrameType);
+    }
 
+    return result;
+}
 
 OFCondition FGParametricMapFrameType::check() const
 {
-  DcmCodeString myFrameType = m_FrameType;
-  OFCondition result = myFrameType.checkValue("4");
-  if (result.good())
-  {
-    OFString val;
-    myFrameType.getOFString(val, 0);
-    if (val == "DERIVED")
+    DcmCodeString myFrameType = m_FrameType;
+    OFCondition result        = myFrameType.checkValue("4");
+    if (result.good())
     {
-      val.clear();
-      myFrameType.getOFString(val, 1);
-      if (val == "PRIMARY")
-      {
-        val.clear();
-        myFrameType.getOFString(val, 1);
-        return EC_Normal;
-      }
-      else
-        DCMFG_ERROR("Frame Type' 2nd value must be \"PRIMARY\" but is \"" << val << "\"");
+        OFString val;
+        myFrameType.getOFString(val, 0);
+        if (val == "DERIVED")
+        {
+            val.clear();
+            myFrameType.getOFString(val, 1);
+            if (val == "PRIMARY")
+            {
+                val.clear();
+                myFrameType.getOFString(val, 1);
+                return EC_Normal;
+            }
+            else
+                DCMFG_ERROR("Frame Type' 2nd value must be \"PRIMARY\" but is \"" << val << "\"");
+        }
+        else
+            DCMFG_ERROR("Frame Type 1st value must be \"DERIVED\" but is \"" << val << "\"");
     }
-    else
-      DCMFG_ERROR("Frame Type 1st value must be \"DERIVED\" but is \"" << val << "\"");
-  }
-  return FG_EC_InvalidData;
+    return FG_EC_InvalidData;
 }
 
-
-OFCondition FGParametricMapFrameType::getFrameType(OFString &value,
-                                                   const signed long pos) const
+OFCondition FGParametricMapFrameType::getFrameType(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromElement(m_FrameType, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_FrameType, value, pos);
 }
 
-
-OFCondition FGParametricMapFrameType::setFrameType(const OFString &value,
-                                                   const OFBool checkValue)
+OFCondition FGParametricMapFrameType::setFrameType(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "4") : EC_Normal;
-  if (result.good())
-    result = m_FrameType.putString(value.c_str());
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "4") : EC_Normal;
+    if (result.good())
+        result = m_FrameType.putString(value.c_str());
+    return result;
 }
index de4b7225ec971f16bd3461a915a13147f2217d55..b4b81d2c7d84636267875768d4ff3d9479032e52 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016-2018, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  */
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcdeftag.h"
-#include "dcmtk/dcmiod/iodutil.h"
+#include "dcmtk/dcmdata/dcuid.h"
 #include "dcmtk/dcmfg/fgpixeltransform.h"
+#include "dcmtk/dcmiod/iodutil.h"
 
 FGPixelValueTransformation::FGPixelValueTransformation()
-: FGBase(DcmFGTypes::EFG_UNDEFINED)
-, m_RescaleIntercept(DCM_RescaleIntercept)
-, m_RescaleSlope(DCM_RescaleSlope)
-, m_RescaleType(DCM_RescaleType)
-, m_UseAsIdentityPixelValueTransformationFG(OFFalse)
+    : FGBase(DcmFGTypes::EFG_PIXELVALUETRANSMETA)
+    , m_RescaleIntercept(DCM_RescaleIntercept)
+    , m_RescaleSlope(DCM_RescaleSlope)
+    , m_RescaleType(DCM_RescaleType)
+    , m_fgSubType(E_PixelValTrans_Normal)
 {
-  m_RescaleIntercept.putOFStringArray("0");
-  m_RescaleSlope.putOFStringArray("1");
-  m_RescaleType.putOFStringArray("US");
+    m_RescaleIntercept.putOFStringArray("0");
+    m_RescaleSlope.putOFStringArray("1");
+    m_RescaleType.putOFStringArray("US");
 }
 
-
 void FGPixelValueTransformation::setUseAsIdentityPixelValueTransformation()
 {
-  m_UseAsIdentityPixelValueTransformationFG = OFTrue;
+    m_fgSubType = E_PixelValTrans_Identity;
 }
 
+void FGPixelValueTransformation::setFGType(const FGPixelValueTransformation::E_PixelValueTransformationSubType fgType)
+{
+    m_fgSubType = fgType;
+}
 
+FGPixelValueTransformation::E_PixelValueTransformationSubType FGPixelValueTransformation::getFGType() const
+{
+    return m_fgSubType;
+}
 
 FGPixelValueTransformation::~FGPixelValueTransformation()
 {
-
 }
 
-
 OFCondition FGPixelValueTransformation::check() const
 {
-  if (m_UseAsIdentityPixelValueTransformationFG)
-  {
+    OFCondition result = EC_Normal;
     Float64 rs, ri;
     rs = ri = 0;
     OFString rt;
-    OFBool ok = OFTrue;
-    if (OFconst_cast(DcmDecimalString*, &m_RescaleIntercept)->getFloat64(ri).good())
-    {
-      if (ri != 0)
-      {
-        DCMFG_ERROR("Rescale Intercept in Identity Pixel Value Transformation FG must be 0 but is set to " << ri);
-        ok = OFFalse;
-      }
-    }
-    else
-    {
-      DCMFG_ERROR("Invalid or no value for Rescale Intercept in Identity Pixel Value Transformation FG (0 is the only valid value");
-      ok = OFFalse;
-    }
-
-    if (OFconst_cast(DcmDecimalString*, &m_RescaleSlope)->getFloat64(rs).good())
+    switch (m_fgSubType)
     {
-      if (rs != 1)
-      {
-        DCMFG_ERROR("Rescale Slope in Identity Pixel Value Transformation FG must be 1 but is set to " << rs);
-        ok = OFFalse;
-      }
+        case E_PixelValTrans_Identity:
+            if (OFconst_cast(DcmDecimalString*, &m_RescaleIntercept)->getFloat64(ri).good())
+            {
+                if (ri != 0)
+                {
+                    DCMFG_ERROR("Rescale Intercept in Identity Pixel Value Transformation FG must be 0 but is set to "
+                                << ri);
+                    result = FG_EC_InvalidData;
+                }
+            }
+            else
+            {
+                DCMFG_ERROR(
+                    "Invalid or no value for Rescale Intercept in Identity Pixel Value Transformation FG (0 is the "
+                    "only valid value");
+                result = FG_EC_InvalidData;
+            }
+
+            if (OFconst_cast(DcmDecimalString*, &m_RescaleSlope)->getFloat64(rs).good())
+            {
+                if (rs != 1)
+                {
+                    DCMFG_ERROR("Rescale Slope in Identity Pixel Value Transformation FG must be 1 but is set to "
+                                << rs);
+                    result = FG_EC_InvalidData;
+                    ;
+                }
+            }
+            else
+            {
+                DCMFG_ERROR("Invalid or no value for Rescale Slope in Identity Pixel Value Transformation FG (1 is the "
+                            "only valid value");
+                result = FG_EC_InvalidData;
+                ;
+            }
+
+            if (OFconst_cast(DcmLongString*, &m_RescaleType)->getOFStringArray(rt).good())
+            {
+                if (rt != "US")
+                {
+                    DCMFG_ERROR("Rescale Type in Identity Pixel Value Transformation FG must be \"US\" but is set to "
+                                << rt);
+                    result = FG_EC_InvalidData;
+                    ;
+                }
+            }
+            else
+            {
+                DCMFG_ERROR(
+                    "Invalid or no value for Rescale Type in Identity Pixel Value Transformation FG (\"US\" is the "
+                    "only valid value");
+                result = FG_EC_InvalidData;
+                ;
+            }
+            break;
+        case E_PixelValTrans_CT:
+        case E_PixelValTrans_Normal:
+        default:
+            // No checks possible
+            break;
     }
-    else
-    {
-      DCMFG_ERROR("Invalid or no value for Rescale Slope in Identity Pixel Value Transformation FG (1 is the only valid value");
-      ok = OFFalse;
-    }
-
-    if (OFconst_cast(DcmLongString*, &m_RescaleType)->getOFStringArray(rt).good())
-    {
-      if (rt != "US")
-      {
-        DCMFG_ERROR("Rescale Type in Identity Pixel Value Transformation FG must be \"US\" but is set to " << rt);
-        ok = OFFalse;
-      }
-    }
-    else
-    {
-      DCMFG_ERROR("Invalid or no value for Rescale Type in Identity Pixel Value Transformation FG (\"US\" is the only valid value");
-      ok = OFFalse;
-    }
-    if (!ok)
-    {
-      return FG_EC_InvalidData;
-    }
-  }
-  return EC_Normal;
+    return result;
 }
 
-
 void FGPixelValueTransformation::clearData()
 {
-  m_RescaleIntercept.clear();
-  m_RescaleSlope.clear();
-  m_RescaleType.clear();
+    m_RescaleIntercept.clear();
+    m_RescaleSlope.clear();
+    m_RescaleType.clear();
 }
 
-
 FGBase* FGPixelValueTransformation::clone() const
 {
-  if(FGPixelValueTransformation* copy = new FGPixelValueTransformation)
-  {
-    copy->m_RescaleIntercept = m_RescaleIntercept;
-    copy->m_RescaleSlope = m_RescaleSlope;
-    copy->m_RescaleType = m_RescaleType;
-    return copy;
-  }
-  return OFnullptr;
+    if (FGPixelValueTransformation* copy = new FGPixelValueTransformation)
+    {
+        copy->m_RescaleIntercept = m_RescaleIntercept;
+        copy->m_RescaleSlope     = m_RescaleSlope;
+        copy->m_RescaleType      = m_RescaleType;
+        return copy;
+    }
+    return OFnullptr;
 }
 
-
 OFCondition FGPixelValueTransformation::read(DcmItem& item)
 {
-  clearData();
-
-  DcmItem* seqItem;
-  OFCondition result;
-
-  seqItem = OFnullptr;
-  result = getItemFromFGSequence(item, DCM_PixelValueTransformationSequence, 0, seqItem);
-  if(result.bad())
-    return result;
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_RescaleIntercept, "1", "1", "Identity Pixel Value Transformation");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_RescaleSlope, "1", "1", "Identity Pixel Value Transformation");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_RescaleType, "1", "1", "Identity Pixel Value Transformation");
+    clearData();
+
+    DcmItem* seqItem;
+    OFCondition result;
+
+    seqItem = OFnullptr;
+    result  = getItemFromFGSequence(item, DCM_PixelValueTransformationSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_RescaleIntercept, "1", "1", fgType2Str().c_str());
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_RescaleSlope, "1", "1", fgType2Str().c_str());
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_RescaleType, "1", "1", fgType2Str().c_str());
+
+    // Try to guess type of Pixel Value Transformation FG by checking for SOP Class
+    OFString sopClass;
+    if (item.getRootItem()->findAndGetOFString(DCM_SOPClassUID, sopClass).good() && !sopClass.empty())
+    {
+        // Identity Pixel Value Transformation FG
+        if ((sopClass == UID_BreastTomosynthesisImageStorage)
+            || (sopClass == UID_BreastProjectionXRayImageStorageForPresentation)
+            || (sopClass == UID_BreastProjectionXRayImageStorageForProcessing)
+            || (sopClass == UID_ParametricMapStorage))
+
+        {
+            DCMFG_DEBUG("FGPixelValueTransformation: Using SOP Class to set Pixel Value Transformation FG to type: "
+                        << fgType2Str());
+            m_fgSubType = E_PixelValTrans_Identity;
+        }
+
+        // CT Pixel Value Transformation FG
+        else if ((sopClass == UID_EnhancedCTImageStorage) || (sopClass == UID_LegacyConvertedEnhancedCTImageStorage))
+        {
+            m_fgSubType = E_PixelValTrans_CT;
+            DCMFG_DEBUG("FGPixelValueTransformation: Using SOP Class to set Pixel Value Transformation FG to type: "
+                        << fgType2Str());
+        }
+        else
+        {
+            m_fgSubType = E_PixelValTrans_Normal;
+            DCMFG_DEBUG(
+                "FGPixelValueTransformation: Setting Pixel Value Transformation FG is of type: " << fgType2Str());
+        }
+    }
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 OFCondition FGPixelValueTransformation::write(DcmItem& item)
 {
-  DcmItem* seqItem;
-  DCMFG_DEBUG("Identity Pixel Value Transformation Macro: Fixing values for Rescale Slope, Intercept and Type to enumerated values '1', '0' and 'US'");
-  m_RescaleSlope.putOFStringArray("1");
-  m_RescaleIntercept.putOFStringArray("0");
-  m_RescaleType.putOFStringArray("US");
+    DcmItem* seqItem;
+    if (m_fgSubType == E_PixelValTrans_Identity)
+    {
+        DCMFG_DEBUG(fgType2Str() << ": Fixing values for Rescale Slope, Intercept and Type to "
+                                    "enumerated values '1', '0' and 'US'");
+        m_RescaleSlope.putOFStringArray("1");
+        m_RescaleIntercept.putOFStringArray("0");
+        m_RescaleType.putOFStringArray("US");
+    }
 
-  seqItem = OFnullptr;
-  OFCondition result = createNewFGSequence(item, DCM_PixelValueTransformationSequence, 0, seqItem);
-  if(result.bad())
-    return result;
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_RescaleIntercept, "1", "1", "Identity Pixel Value Transformation");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_RescaleSlope, "1", "1", "Identity Pixel Value Transformation");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_RescaleType, "1", "1", "Identity Pixel Value Transformation");
+    seqItem            = OFnullptr;
+    OFCondition result = createNewFGSequence(item, DCM_PixelValueTransformationSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_RescaleIntercept, "1", "1", fgType2Str().c_str());
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_RescaleSlope, "1", "1", fgType2Str().c_str());
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_RescaleType, "1", "1", fgType2Str().c_str());
 
-  return result;
+    return result;
 }
 
-
 int FGPixelValueTransformation::compare(const FGBase& rhs) const
 {
-  int result = FGBase::compare(rhs);
-  if(result == 0)
-  {
-    const FGPixelValueTransformation* myRhs = OFstatic_cast(const FGPixelValueTransformation*, &rhs);
-    if (!myRhs)
-      return -1;
-
-    // Compare all elements
-    result = m_RescaleIntercept.compare(myRhs->m_RescaleIntercept);
-    if (result == 0) result = m_RescaleSlope.compare(myRhs->m_RescaleSlope);
-    if (result == 0) result = m_RescaleType.compare(myRhs->m_RescaleType);
-  }
+    int result = FGBase::compare(rhs);
+    if (result == 0)
+    {
+        const FGPixelValueTransformation* myRhs = OFstatic_cast(const FGPixelValueTransformation*, &rhs);
+        if (!myRhs)
+            return -1;
+
+        // Compare all elements
+        result = m_RescaleIntercept.compare(myRhs->m_RescaleIntercept);
+        if (result == 0)
+            result = m_RescaleSlope.compare(myRhs->m_RescaleSlope);
+        if (result == 0)
+            result = m_RescaleType.compare(myRhs->m_RescaleType);
+    }
 
-  return result;
+    return result;
 }
 
-
-OFCondition FGPixelValueTransformation::getRescaleIntercept(OFString &value,
-                                                                    const signed long pos) const
+OFCondition FGPixelValueTransformation::getRescaleIntercept(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromElement(m_RescaleIntercept, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_RescaleIntercept, value, pos);
 }
 
-
-OFCondition FGPixelValueTransformation::getRescaleSlope(OFString &value,
-                                                                const signed long pos) const
+OFCondition FGPixelValueTransformation::getRescaleSlope(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromElement(m_RescaleSlope, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_RescaleSlope, value, pos);
 }
 
-
-OFCondition FGPixelValueTransformation::getRescaleType(OFString &value,
-                                                               const signed long pos) const
+OFCondition FGPixelValueTransformation::getRescaleType(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromElement(m_RescaleType, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_RescaleType, value, pos);
 }
 
-
-OFCondition FGPixelValueTransformation::setRescaleIntercept(const OFString &value,
-                                                                    const OFBool checkValue)
+OFCondition FGPixelValueTransformation::setRescaleIntercept(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_RescaleIntercept.putString(value.c_str());
-  return result;
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_RescaleIntercept.putString(value.c_str());
+    return result;
 }
 
-
-OFCondition FGPixelValueTransformation::setRescaleSlope(const OFString &value,
-                                                                const OFBool checkValue)
+OFCondition FGPixelValueTransformation::setRescaleSlope(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_RescaleSlope.putString(value.c_str());
-  return result;
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_RescaleSlope.putString(value.c_str());
+    return result;
 }
 
-
-OFCondition FGPixelValueTransformation::setRescaleType(const OFString &value,
-                                                               const OFBool checkValue)
+OFCondition FGPixelValueTransformation::setRescaleType(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_RescaleType.putString(value.c_str());
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_RescaleType.putString(value.c_str());
+    return result;
 }
 
+OFString FGPixelValueTransformation::fgType2Str()
+{
+    OFString result;
+    switch (m_fgSubType)
+    {
+        case E_PixelValTrans_Normal:
+            result = "Pixel Value Transformation";
+            break;
+        case E_PixelValTrans_Identity:
+            result = "Identity Pixel Value Transformation";
+            break;
+        case E_PixelValTrans_CT:
+            result = "CT Pixel Value Transformation";
+            break;
+        default:
+            DCMFG_WARN("Internal error: Unknown value for enum E_PixelValueTransformationType in fgType2Str(): "
+                       << m_fgSubType);
+            result = "";
+    }
+    return result;
+}
index 76bb4bb97e4432196b8fbad545b0c4229abcc652..61a432af77abc4ccd2e922f9d6fd80d0e06ef058 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmfg/fgpixmsr.h"
+
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgpixmsr.h"
 #include "dcmtk/dcmiod/iodutil.h"
 
-
 FGPixelMeasures::FGPixelMeasures()
-: FGBase(DcmFGTypes::EFG_PIXELMEASURES),
-  m_PixelSpacing(DCM_PixelSpacing),
-  m_SliceThickness(DCM_SliceThickness),
-  m_SpacingBetweenSlices(DCM_SpacingBetweenSlices)
+    : FGBase(DcmFGTypes::EFG_PIXELMEASURES)
+    , m_PixelSpacing(DCM_PixelSpacing)
+    , m_SliceThickness(DCM_SliceThickness)
+    , m_SpacingBetweenSlices(DCM_SpacingBetweenSlices)
 {
 }
 
-
 FGPixelMeasures::~FGPixelMeasures()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
 FGBase* FGPixelMeasures::clone() const
 {
-  FGPixelMeasures* copy = new FGPixelMeasures();
-  if (copy)
-  {
-    copy->m_PixelSpacing = this->m_PixelSpacing;
-    copy->m_SliceThickness = this->m_SliceThickness;
-    copy->m_SpacingBetweenSlices = this->m_SpacingBetweenSlices;
-  }
-  return copy;
+    FGPixelMeasures* copy = new FGPixelMeasures();
+    if (copy)
+    {
+        copy->m_PixelSpacing         = this->m_PixelSpacing;
+        copy->m_SliceThickness       = this->m_SliceThickness;
+        copy->m_SpacingBetweenSlices = this->m_SpacingBetweenSlices;
+    }
+    return copy;
 }
 
-
 void FGPixelMeasures::clearData()
 {
-  m_PixelSpacing.clear();
-  m_SliceThickness.clear();
-  m_SpacingBetweenSlices.clear();
+    m_PixelSpacing.clear();
+    m_SliceThickness.clear();
+    m_SpacingBetweenSlices.clear();
 }
 
-
 OFCondition FGPixelMeasures::check() const
 {
-  // Checks in read() and write() are sufficient for now
-  return EC_Normal;
+    // Checks in read() and write() are sufficient for now
+    return EC_Normal;
 }
 
-
 int FGPixelMeasures::compare(const FGBase& rhs) const
 {
-  int result = FGBase::compare(rhs);
-  if (result != 0)
-    return result;
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
 
-  const FGPixelMeasures* myRhs = OFstatic_cast(const FGPixelMeasures*, &rhs);
-  if (!myRhs)
-    return -1;
+    const FGPixelMeasures* myRhs = OFstatic_cast(const FGPixelMeasures*, &rhs);
+    if (!myRhs)
+        return -1;
 
-  // Compare all elements
-  result = m_PixelSpacing.compare(myRhs->m_PixelSpacing);
-  if (result == 0)
-    result = m_SliceThickness.compare(myRhs->m_SliceThickness);
-  if (result == 0)
-    result = m_SpacingBetweenSlices.compare(myRhs->m_SpacingBetweenSlices);
+    // Compare all elements
+    result = m_PixelSpacing.compare(myRhs->m_PixelSpacing);
+    if (result == 0)
+        result = m_SliceThickness.compare(myRhs->m_SliceThickness);
+    if (result == 0)
+        result = m_SpacingBetweenSlices.compare(myRhs->m_SpacingBetweenSlices);
 
-  return result;
+    return result;
 }
 
-
 /// Read from Frame Content Sequence
 OFCondition FGPixelMeasures::read(DcmItem& item)
 {
-  clearData();
+    clearData();
 
-  OFCondition result;
-  DcmItem* seqItem = NULL;
-  result = getItemFromFGSequence(item, DCM_PixelMeasuresSequence, 0, seqItem);
-  if (result.bad())
-    return result;
+    OFCondition result;
+    DcmItem* seqItem = NULL;
+    result           = getItemFromFGSequence(item, DCM_PixelMeasuresSequence, 0, seqItem);
+    if (result.bad())
+        return result;
 
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_PixelSpacing,   "2", "1C", "PixelMeasuresMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_SliceThickness, "1", "1C", "PixelMeasuresMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_SpacingBetweenSlices, "1", "3", "PixelMeasuresMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_PixelSpacing, "2", "1C", "PixelMeasuresMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_SliceThickness, "1", "1C", "PixelMeasuresMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_SpacingBetweenSlices, "1", "3", "PixelMeasuresMacro");
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
 OFCondition FGPixelMeasures::write(DcmItem& item)
 {
-  DcmItem* seqItem = NULL;
-  OFCondition result = createNewFGSequence(item, DCM_PixelMeasuresSequence, 0, seqItem);
-  if (result.bad())
-    return result;
+    DcmItem* seqItem   = NULL;
+    OFCondition result = createNewFGSequence(item, DCM_PixelMeasuresSequence, 0, seqItem);
+    if (result.bad())
+        return result;
 
-  // --- write frame content macro attributes ---
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_PixelSpacing, "2", "1C", "PixelMeasuresMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_SliceThickness, "1", "1C", "PixelMeasuresMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_SpacingBetweenSlices, "1", "3", "PixelMeasuresMacro");
+    // --- write frame content macro attributes ---
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_PixelSpacing, "2", "1C", "PixelMeasuresMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_SliceThickness, "1", "1C", "PixelMeasuresMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_SpacingBetweenSlices, "1", "3", "PixelMeasuresMacro");
 
-  return result;
+    return result;
 }
 
-
-OFCondition FGPixelMeasures::getPixelSpacing(Float64& value,
-                                             const signed long pos)
+OFCondition FGPixelMeasures::getPixelSpacing(Float64& value, const unsigned long pos)
 {
-  return m_PixelSpacing.getFloat64(value, pos);
+    return m_PixelSpacing.getFloat64(value, pos);
 }
 
-
-OFCondition FGPixelMeasures:: getSliceThickness(Float64& value,
-                                                const signed long pos)
+OFCondition FGPixelMeasures::getSliceThickness(Float64& value, const unsigned long pos)
 {
-  return m_SliceThickness.getFloat64(value, pos);
+    return m_SliceThickness.getFloat64(value, pos);
 }
 
-
-OFCondition FGPixelMeasures:: getSpacingBetweenSlices(Float64& value,
-                                                      const signed long pos)
+OFCondition FGPixelMeasures::getSpacingBetweenSlices(Float64& value, const unsigned long pos)
 {
-  return m_SpacingBetweenSlices.getFloat64(value, pos);
+    return m_SpacingBetweenSlices.getFloat64(value, pos);
 }
 
-
-OFCondition FGPixelMeasures::setPixelSpacing(const OFString& value,
-                                             const OFBool checkValue)
+OFCondition FGPixelMeasures::setPixelSpacing(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "2") : EC_Normal;
-  if (result.good())
-  {
-    result = m_PixelSpacing.putOFStringArray(value);
-  }
-  return result;
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "2") : EC_Normal;
+    if (result.good())
+    {
+        result = m_PixelSpacing.putOFStringArray(value);
+    }
+    return result;
 }
 
-
-OFCondition FGPixelMeasures::setSliceThickness(const OFString& value,
-                                               const OFBool checkValue)
+OFCondition FGPixelMeasures::setSliceThickness(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-  {
-    result = m_SliceThickness.putOFStringArray(value);
-  }
-  return result;
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+    {
+        result = m_SliceThickness.putOFStringArray(value);
+    }
+    return result;
 }
 
-OFCondition FGPixelMeasures::setSpacingBetweenSlices(const OFString& value,
-                                                     const OFBool checkValue)
+OFCondition FGPixelMeasures::setSpacingBetweenSlices(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-  {
-    result = m_SpacingBetweenSlices.putOFStringArray(value);
-  }
-  return result;
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+    {
+        result = m_SpacingBetweenSlices.putOFStringArray(value);
+    }
+    return result;
 }
index 36a00dca31de5ca1f3dba4f8d167a0e538dd8d7a..8bc736061872300a3715e05e8605840bfc528cda 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmfg/fgplanor.h"
-#include "dcmtk/dcmfg/fgfact.h"
+
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgfact.h"
+#include "dcmtk/dcmfg/fgplanor.h"
 #include "dcmtk/dcmiod/iodutil.h"
 
-
-FGPlaneOrientationPatient::FGPlaneOrientationPatient() :
-  FGBase(DcmFGTypes::EFG_PLANEORIENTPATIENT),
-  m_ImageOrientationPatient(DCM_ImageOrientationPatient)
+FGPlaneOrientationPatient::FGPlaneOrientationPatient()
+    : FGBase(DcmFGTypes::EFG_PLANEORIENTPATIENT)
+    , m_ImageOrientationPatient(DCM_ImageOrientationPatient)
 {
 }
 
 /// clear old values
 void FGPlaneOrientationPatient::clearData()
 {
-  m_ImageOrientationPatient.clear();
+    m_ImageOrientationPatient.clear();
 }
 
-
 OFCondition FGPlaneOrientationPatient::check() const
 {
-  // Checks in read() and write() are sufficient for now
-  return EC_Normal;
+    // Checks in read() and write() are sufficient for now
+    return EC_Normal;
 }
 
-
 FGBase* FGPlaneOrientationPatient::clone() const
 {
-  FGPlaneOrientationPatient* copy = new FGPlaneOrientationPatient();
-  if (copy)
-  {
-    copy->m_ImageOrientationPatient = this->m_ImageOrientationPatient;
-  }
-  return copy;
+    FGPlaneOrientationPatient* copy = new FGPlaneOrientationPatient();
+    if (copy)
+    {
+        copy->m_ImageOrientationPatient = this->m_ImageOrientationPatient;
+    }
+    return copy;
 }
 
-
 FGPlaneOrientationPatient* FGPlaneOrientationPatient::createMinimal(const OFString& imageOrientationPatientRowX,
                                                                     const OFString& imageOrientationPatientRowY,
                                                                     const OFString& imageOrientationPatientRowZ,
@@ -65,99 +61,94 @@ FGPlaneOrientationPatient* FGPlaneOrientationPatient::createMinimal(const OFStri
                                                                     const OFString& imageOrientationPatientColY,
                                                                     const OFString& imageOrientationPatientColZ)
 {
-  FGPlaneOrientationPatient *fg = OFstatic_cast(FGPlaneOrientationPatient*, FGFactory::instance().create(DcmFGTypes::EFG_PLANEORIENTPATIENT));
-  if (fg)
-  {
-    OFCondition result = fg->setImageOrientationPatient(imageOrientationPatientRowX,
-                                                        imageOrientationPatientRowY,
-                                                        imageOrientationPatientRowZ,
-                                                        imageOrientationPatientColX,
-                                                        imageOrientationPatientColY,
-                                                        imageOrientationPatientColZ);
-    if (result.bad())
+    FGPlaneOrientationPatient* fg
+        = OFstatic_cast(FGPlaneOrientationPatient*, FGFactory::instance().create(DcmFGTypes::EFG_PLANEORIENTPATIENT));
+    if (fg)
     {
-      DCMFG_ERROR("Could not create new FGPlaneOrientationPatient: Invalid data for Image Orientation Patient: " << result.text());
-      delete fg;
-      return NULL;
+        OFCondition result = fg->setImageOrientationPatient(imageOrientationPatientRowX,
+                                                            imageOrientationPatientRowY,
+                                                            imageOrientationPatientRowZ,
+                                                            imageOrientationPatientColX,
+                                                            imageOrientationPatientColY,
+                                                            imageOrientationPatientColZ);
+        if (result.bad())
+        {
+            DCMFG_ERROR("Could not create new FGPlaneOrientationPatient: Invalid data for Image Orientation Patient: "
+                        << result.text());
+            delete fg;
+            return NULL;
+        }
     }
-  }
-  return fg;
+    return fg;
 }
 
-
-
 /// Read from Plane Position Sequence
 OFCondition FGPlaneOrientationPatient::read(DcmItem& item)
 {
-  clearData();
+    clearData();
 
-  DcmItem *seqItem = NULL;
-  OFCondition result = getItemFromFGSequence(item, DCM_PlaneOrientationSequence, 0, seqItem);
-  if (result.bad())
-    return result;
+    DcmItem* seqItem   = NULL;
+    OFCondition result = getItemFromFGSequence(item, DCM_PlaneOrientationSequence, 0, seqItem);
+    if (result.bad())
+        return result;
 
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_ImageOrientationPatient,   "6", "1C", "PlaneOrientationPatient");
+    DcmIODUtil::getAndCheckElementFromDataset(
+        *seqItem, m_ImageOrientationPatient, "6", "1C", "PlaneOrientationPatient");
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 OFCondition FGPlaneOrientationPatient::write(DcmItem& item)
 {
-  DcmItem *seqItem = NULL;
-  OFCondition result = createNewFGSequence(item, DCM_PlaneOrientationSequence, 0, seqItem);
-  if (result.bad())
-    return result;
+    DcmItem* seqItem   = NULL;
+    OFCondition result = createNewFGSequence(item, DCM_PlaneOrientationSequence, 0, seqItem);
+    if (result.bad())
+        return result;
 
-  // --- write plane position (patient) attributes ---
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_ImageOrientationPatient, "6", "1C", "PlaneOrientationPatient");
+    // --- write plane position (patient) attributes ---
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_ImageOrientationPatient, "6", "1C", "PlaneOrientationPatient");
 
-  return result;
+    return result;
 }
 
-
-
 int FGPlaneOrientationPatient::compare(const FGBase& rhs) const
 {
-  int result = FGBase::compare(rhs);
-  if (result == 0)
-  {
-    const FGPlaneOrientationPatient* myRhs = OFstatic_cast(const FGPlaneOrientationPatient*, &rhs);
-    if (!myRhs)
-      return -1;
-
-    // Compare all elements
-    result = m_ImageOrientationPatient.compare(myRhs->m_ImageOrientationPatient);
-  }
-
-  return result;
-}
-
+    int result = FGBase::compare(rhs);
+    if (result == 0)
+    {
+        const FGPlaneOrientationPatient* myRhs = OFstatic_cast(const FGPlaneOrientationPatient*, &rhs);
+        if (!myRhs)
+            return -1;
 
-OFCondition FGPlaneOrientationPatient::getImageOrientationPatient(OFString& value,
-                                                                  const signed long pos = 0)
+        // Compare all elements
+        result = m_ImageOrientationPatient.compare(myRhs->m_ImageOrientationPatient);
+    }
 
-{
-  return DcmIODUtil::getStringValueFromElement(m_ImageOrientationPatient, value, pos);
+    return result;
 }
 
+OFCondition FGPlaneOrientationPatient::getImageOrientationPatient(OFString& value, const signed long pos = 0)
 
-OFCondition FGPlaneOrientationPatient::getImageOrientationPatient(Float64& rowX,
-                                                                  Float64& rowY,
-                                                                  Float64& rowZ,
-                                                                  Float64& colX,
-                                                                  Float64& colY,
-                                                                  Float64& colZ)
 {
-  OFCondition result = m_ImageOrientationPatient.getFloat64(rowX, 0);
-  if (result.good()) m_ImageOrientationPatient.getFloat64(rowY, 1);
-  if (result.good()) m_ImageOrientationPatient.getFloat64(rowZ, 2);
-  if (result.good()) m_ImageOrientationPatient.getFloat64(colX, 3);
-  if (result.good()) m_ImageOrientationPatient.getFloat64(colY, 4);
-  if (result.good()) m_ImageOrientationPatient.getFloat64(colZ, 5);
-  return result;
+    return DcmIODUtil::getStringValueFromElement(m_ImageOrientationPatient, value, pos);
 }
 
+OFCondition FGPlaneOrientationPatient::getImageOrientationPatient(
+    Float64& rowX, Float64& rowY, Float64& rowZ, Float64& colX, Float64& colY, Float64& colZ)
+{
+    OFCondition result = m_ImageOrientationPatient.getFloat64(rowX, 0);
+    if (result.good())
+        m_ImageOrientationPatient.getFloat64(rowY, 1);
+    if (result.good())
+        m_ImageOrientationPatient.getFloat64(rowZ, 2);
+    if (result.good())
+        m_ImageOrientationPatient.getFloat64(colX, 3);
+    if (result.good())
+        m_ImageOrientationPatient.getFloat64(colY, 4);
+    if (result.good())
+        m_ImageOrientationPatient.getFloat64(colZ, 5);
+    return result;
+}
 
 OFCondition FGPlaneOrientationPatient::setImageOrientationPatient(const OFString& rowX,
                                                                   const OFString& rowY,
@@ -167,21 +158,25 @@ OFCondition FGPlaneOrientationPatient::setImageOrientationPatient(const OFString
                                                                   const OFString& colZ,
                                                                   const OFBool checkValue)
 {
-  OFString str(rowX); str += "\\";
-  str += rowY; str += "\\";
-  str += rowZ; str += "\\";
-  str += colX; str += "\\";
-  str += colY; str += "\\";
-  str += colZ;
-
-  OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(str, "6") : EC_Normal;
-  if (result.good())
-    result = m_ImageOrientationPatient.putOFStringArray(str);
-  return result;
+    OFString str(rowX);
+    str += "\\";
+    str += rowY;
+    str += "\\";
+    str += rowZ;
+    str += "\\";
+    str += colX;
+    str += "\\";
+    str += colY;
+    str += "\\";
+    str += colZ;
+
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(str, "6") : EC_Normal;
+    if (result.good())
+        result = m_ImageOrientationPatient.putOFStringArray(str);
+    return result;
 }
 
-
 FGPlaneOrientationPatient::~FGPlaneOrientationPatient()
 {
-  // nothing to do
+    // nothing to do
 }
index c7d411712476c348fbe10d416023c020a8026fc9..71ec08e5194cf5856cc3123015353c7bec236a02 100644 (file)
  */
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmdata/dcvrfd.h"
+
 #include "dcmtk/dcmdata/dcdeftag.h"
-#include "dcmtk/dcmiod/iodutil.h"
+#include "dcmtk/dcmdata/dcvrfd.h"
 #include "dcmtk/dcmfg/fgplanorvol.h"
 #include "dcmtk/dcmfg/fgtypes.h"
-
+#include "dcmtk/dcmiod/iodutil.h"
 
 // Constructor
-FGPlaneOrientationVolume::FGPlaneOrientationVolume() :
-  FGBase(DcmFGTypes::EFG_PLANEORIENTVOLUME),
-  m_ImageOrientationVolume(DCM_ImageOrientationVolume)
+FGPlaneOrientationVolume::FGPlaneOrientationVolume()
+    : FGBase(DcmFGTypes::EFG_PLANEORIENTVOLUME)
+    , m_ImageOrientationVolume(DCM_ImageOrientationVolume)
 {
 }
 
-
 FGPlaneOrientationVolume::~FGPlaneOrientationVolume()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
 FGBase* FGPlaneOrientationVolume::clone() const
 {
-  FGPlaneOrientationVolume* copy = new FGPlaneOrientationVolume();
-  if (copy)
-  {
-    copy->m_ImageOrientationVolume = this->m_ImageOrientationVolume;
-  }
-  return copy;
+    FGPlaneOrientationVolume* copy = new FGPlaneOrientationVolume();
+    if (copy)
+    {
+        copy->m_ImageOrientationVolume = this->m_ImageOrientationVolume;
+    }
+    return copy;
 }
 
-
 void FGPlaneOrientationVolume::clearData()
 {
-  m_ImageOrientationVolume.clear();
+    m_ImageOrientationVolume.clear();
 }
 
-
 OFCondition FGPlaneOrientationVolume::check() const
 {
-  // Checks in read() and write() are sufficient for now
-  return EC_Normal;
+    // Checks in read() and write() are sufficient for now
+    return EC_Normal;
 }
 
-
 // --- get() functionality ---
 
-OFCondition FGPlaneOrientationVolume::getImageOrientationVolume(Float64& value,
-                                                                const long unsigned int pos)
+OFCondition FGPlaneOrientationVolume::getImageOrientationVolume(Float64& value, const long unsigned int pos)
 {
-  return m_ImageOrientationVolume.getFloat64(value, pos);
+    return m_ImageOrientationVolume.getFloat64(value, pos);
 }
 
-
-
-OFCondition FGPlaneOrientationVolume::getImageOrientationVolume(Float64& rowX,
-                                                                Float64& rowY,
-                                                                Float64& rowZ,
-                                                                Float64& colX,
-                                                                Float64& colY,
-                                                                Float64& colZ)
+OFCondition FGPlaneOrientationVolume::getImageOrientationVolume(
+    Float64& rowX, Float64& rowY, Float64& rowZ, Float64& colX, Float64& colY, Float64& colZ)
 {
-  OFCondition result = m_ImageOrientationVolume.getFloat64(rowX, 0);
-  if (result.good()) result = m_ImageOrientationVolume.getFloat64(rowY, 1);
-  if (result.good()) result = m_ImageOrientationVolume.getFloat64(rowZ, 2);
-  if (result.good()) result = m_ImageOrientationVolume.getFloat64(colX, 3);
-  if (result.good()) result = m_ImageOrientationVolume.getFloat64(colY, 4);
-  if (result.good()) result = m_ImageOrientationVolume.getFloat64(colZ, 5);
-  return result;
+    OFCondition result = m_ImageOrientationVolume.getFloat64(rowX, 0);
+    if (result.good())
+        result = m_ImageOrientationVolume.getFloat64(rowY, 1);
+    if (result.good())
+        result = m_ImageOrientationVolume.getFloat64(rowZ, 2);
+    if (result.good())
+        result = m_ImageOrientationVolume.getFloat64(colX, 3);
+    if (result.good())
+        result = m_ImageOrientationVolume.getFloat64(colY, 4);
+    if (result.good())
+        result = m_ImageOrientationVolume.getFloat64(colZ, 5);
+    return result;
 }
 
-
 // --- set() functionality ---
 
-
 OFCondition FGPlaneOrientationVolume::setImageOrientationVolume(const Float64& rowX,
                                                                 const Float64& rowY,
                                                                 const Float64& rowZ,
@@ -103,60 +94,59 @@ OFCondition FGPlaneOrientationVolume::setImageOrientationVolume(const Float64& r
                                                                 const Float64& colZ,
                                                                 const OFBool)
 {
-  OFCondition result = m_ImageOrientationVolume.putFloat64(rowX, 0);
-  if (result.good()) m_ImageOrientationVolume.putFloat64(rowY, 1);
-  if (result.good()) m_ImageOrientationVolume.putFloat64(rowZ, 2);
-  if (result.good()) m_ImageOrientationVolume.putFloat64(colX, 3);
-  if (result.good()) m_ImageOrientationVolume.putFloat64(colY, 4);
-  if (result.good()) m_ImageOrientationVolume.putFloat64(colZ, 5);
-  return result;
+    OFCondition result = m_ImageOrientationVolume.putFloat64(rowX, 0);
+    if (result.good())
+        m_ImageOrientationVolume.putFloat64(rowY, 1);
+    if (result.good())
+        m_ImageOrientationVolume.putFloat64(rowZ, 2);
+    if (result.good())
+        m_ImageOrientationVolume.putFloat64(colX, 3);
+    if (result.good())
+        m_ImageOrientationVolume.putFloat64(colY, 4);
+    if (result.good())
+        m_ImageOrientationVolume.putFloat64(colZ, 5);
+    return result;
 }
 
-
 /// Read Plane Orientation (Volume) Sequence from given item
 OFCondition FGPlaneOrientationVolume::read(DcmItem& item)
 {
-  clearData();
+    clearData();
 
-  DcmItem* seqItem = NULL;
-  OFCondition result = getItemFromFGSequence(item, DCM_PlaneOrientationVolumeSequence, 0, seqItem);
-  if (result.bad())
-    return result;
-
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_ImageOrientationVolume, "6", "1", "PlaneOrientationVolume");
+    DcmItem* seqItem   = NULL;
+    OFCondition result = getItemFromFGSequence(item, DCM_PlaneOrientationVolumeSequence, 0, seqItem);
+    if (result.bad())
+        return result;
 
-  return EC_Normal;
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_ImageOrientationVolume, "6", "1", "PlaneOrientationVolume");
 
+    return EC_Normal;
 }
 
 /// Writes single Plane Orientation (Volume) Sequence into given item
 OFCondition FGPlaneOrientationVolume::write(DcmItem& item)
 {
-  DcmItem *seqItem = NULL;
-  OFCondition result = createNewFGSequence(item, DCM_PlaneOrientationVolumeSequence, 0, seqItem);
-  if (result.bad())
-    return result;
+    DcmItem* seqItem   = NULL;
+    OFCondition result = createNewFGSequence(item, DCM_PlaneOrientationVolumeSequence, 0, seqItem);
+    if (result.bad())
+        return result;
 
-  // --- write frame content macro attributes ---
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_ImageOrientationVolume, "6", "1", "PlaneOrientationVolume");
-  return result;
+    // --- write frame content macro attributes ---
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_ImageOrientationVolume, "6", "1", "PlaneOrientationVolume");
+    return result;
 }
 
-
 int FGPlaneOrientationVolume::compare(const FGBase& rhs) const
 {
-  int result = FGBase::compare(rhs);
-  if (result != 0)
-    return result;
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
 
-  const FGPlaneOrientationVolume* myRhs = OFstatic_cast(const FGPlaneOrientationVolume*, &rhs);
-  if (!myRhs)
-    return -1;
+    const FGPlaneOrientationVolume* myRhs = OFstatic_cast(const FGPlaneOrientationVolume*, &rhs);
+    if (!myRhs)
+        return -1;
 
-  // Compare all elements
-  result = m_ImageOrientationVolume.compare(myRhs->m_ImageOrientationVolume);
-  return result;
+    // Compare all elements
+    result = m_ImageOrientationVolume.compare(myRhs->m_ImageOrientationVolume);
+    return result;
 }
-
-
-
index b1c461097cfe84f3480d3fba1c8ffedc5246be4d..cc225792a2b486001d803a1f8293642c0e4d458e 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  */
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmfg/fgplanpo.h"
-#include "dcmtk/dcmfg/fgfact.h"
+
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgfact.h"
+#include "dcmtk/dcmfg/fgplanpo.h"
 #include "dcmtk/dcmiod/iodutil.h"
 
-FGPlanePosPatient::FGPlanePosPatient() :
-  FGBase(DcmFGTypes::EFG_PLANEPOSPATIENT),
-  m_ImagePositionPatient(DCM_ImagePositionPatient)
+FGPlanePosPatient::FGPlanePosPatient()
+    : FGBase(DcmFGTypes::EFG_PLANEPOSPATIENT)
+    , m_ImagePositionPatient(DCM_ImagePositionPatient)
 {
 }
 
 FGBase* FGPlanePosPatient::clone() const
 {
-  FGPlanePosPatient* copy = new FGPlanePosPatient();
-  if (copy)
-  {
-    copy->m_ImagePositionPatient = this->m_ImagePositionPatient;
-  }
-  return copy;
+    FGPlanePosPatient* copy = new FGPlanePosPatient();
+    if (copy)
+    {
+        copy->m_ImagePositionPatient = this->m_ImagePositionPatient;
+    }
+    return copy;
 }
 
-
 FGPlanePosPatient* FGPlanePosPatient::createMinimal(const OFString& imagePositionPatientX,
                                                     const OFString& imagePositionPatientY,
                                                     const OFString& imagePositionPatientZ)
 {
-  FGPlanePosPatient *fg = OFstatic_cast(FGPlanePosPatient*, FGFactory::instance().create(DcmFGTypes::EFG_PLANEPOSPATIENT));
-  if (fg)
-  {
-    OFCondition result = fg->setImagePositionPatient(imagePositionPatientX, imagePositionPatientY, imagePositionPatientZ);
-    if (result.bad())
+    FGPlanePosPatient* fg
+        = OFstatic_cast(FGPlanePosPatient*, FGFactory::instance().create(DcmFGTypes::EFG_PLANEPOSPATIENT));
+    if (fg)
     {
-      DCMFG_ERROR("Could not create new FGPlanePosPatient: Invalid data for Image Position Patient: " << result.text());
-      delete fg;
-      return NULL;
+        OFCondition result
+            = fg->setImagePositionPatient(imagePositionPatientX, imagePositionPatientY, imagePositionPatientZ);
+        if (result.bad())
+        {
+            DCMFG_ERROR(
+                "Could not create new FGPlanePosPatient: Invalid data for Image Position Patient: " << result.text());
+            delete fg;
+            return NULL;
+        }
     }
-  }
-  return fg;
+    return fg;
 }
 
-
-
 /// clear old values
 void FGPlanePosPatient::clearData()
 {
-  m_ImagePositionPatient.clear();
+    m_ImagePositionPatient.clear();
 }
 
-
 OFCondition FGPlanePosPatient::check() const
 {
-  // Checks in read() and write() are sufficient for now
-  return EC_Normal;
+    // Checks in read() and write() are sufficient for now
+    return EC_Normal;
 }
 
-
 /// Read from Plane Position Sequence
 OFCondition FGPlanePosPatient::read(DcmItem& item)
 {
-  clearData();
+    clearData();
 
-  DcmItem* seqItem = NULL;
-  OFCondition result =  getItemFromFGSequence(item, DCM_PlanePositionSequence, 0, seqItem);
-  if (result.bad())
-    return result;
+    DcmItem* seqItem   = NULL;
+    OFCondition result = getItemFromFGSequence(item, DCM_PlanePositionSequence, 0, seqItem);
+    if (result.bad())
+        return result;
 
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_ImagePositionPatient,   "3", "1C", "PlanePositionSequence");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_ImagePositionPatient, "3", "1C", "PlanePositionSequence");
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 OFCondition FGPlanePosPatient::write(DcmItem& item)
 {
-  DcmItem* seqItem = NULL;
-  OFCondition result = createNewFGSequence(item, DCM_PlanePositionSequence, 0, seqItem);
-  if (result.bad())
-    return result;
+    DcmItem* seqItem   = NULL;
+    OFCondition result = createNewFGSequence(item, DCM_PlanePositionSequence, 0, seqItem);
+    if (result.bad())
+        return result;
 
-  // --- write plane position (patient) attributes ---
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_ImagePositionPatient, "3", "1C", "PlanePositionSequence");
+    // --- write plane position (patient) attributes ---
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_ImagePositionPatient, "3", "1C", "PlanePositionSequence");
 
-  return result;
+    return result;
 }
 
-
 int FGPlanePosPatient::compare(const FGBase& rhs) const
 {
-  int result = FGBase::compare(rhs);
-  if (result == 0)
-  {
-    const FGPlanePosPatient* myRhs = OFstatic_cast(const FGPlanePosPatient*, &rhs);
-    if (!myRhs)
-      return -1;
-
-    // Compare all elements
-    result = m_ImagePositionPatient.compare(myRhs->m_ImagePositionPatient);
-  }
-
-  return result;
-}
+    int result = FGBase::compare(rhs);
+    if (result == 0)
+    {
+        const FGPlanePosPatient* myRhs = OFstatic_cast(const FGPlanePosPatient*, &rhs);
+        if (!myRhs)
+            return -1;
 
+        // Compare all elements
+        result = m_ImagePositionPatient.compare(myRhs->m_ImagePositionPatient);
+    }
 
+    return result;
+}
 
-OFCondition FGPlanePosPatient::getImagePositionPatient(OFString& value,
-                                                       const signed long pos = 0)
+OFCondition FGPlanePosPatient::getImagePositionPatient(OFString& value, const signed long pos = 0)
 
 {
-  return DcmIODUtil::getStringValueFromElement(m_ImagePositionPatient, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_ImagePositionPatient, value, pos);
 }
 
-
-OFCondition FGPlanePosPatient::getImagePositionPatient(Float64& coordinateX,
-                                                       Float64& coordinateY,
-                                                       Float64& coordinateZ)
+OFCondition FGPlanePosPatient::getImagePositionPatient(Float64& coordinateX, Float64& coordinateY, Float64& coordinateZ)
 {
-  OFCondition result = m_ImagePositionPatient.getFloat64(coordinateX, 0);
-  if (result.good()) result = m_ImagePositionPatient.getFloat64(coordinateY, 1);
-  if (result.good()) result = m_ImagePositionPatient.getFloat64(coordinateZ, 2);
-  return result;
+    OFCondition result = m_ImagePositionPatient.getFloat64(coordinateX, 0);
+    if (result.good())
+        result = m_ImagePositionPatient.getFloat64(coordinateY, 1);
+    if (result.good())
+        result = m_ImagePositionPatient.getFloat64(coordinateZ, 2);
+    return result;
 }
 
-
 OFCondition FGPlanePosPatient::setImagePositionPatient(const OFString& coordinateX,
                                                        const OFString& coordinateY,
                                                        const OFString& coordinateZ,
@@ -150,19 +142,18 @@ OFCondition FGPlanePosPatient::setImagePositionPatient(const OFString& coordinat
 
 {
 
-  OFString str(coordinateX);
-  str += "\\";
-  str += coordinateY;
-  str += "\\";
-  str += coordinateZ;
-  OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(str, "3") : EC_Normal;
-  if (result.good())
-    result = m_ImagePositionPatient.putOFStringArray(str);
-  return result;
+    OFString str(coordinateX);
+    str += "\\";
+    str += coordinateY;
+    str += "\\";
+    str += coordinateZ;
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(str, "3") : EC_Normal;
+    if (result.good())
+        result = m_ImagePositionPatient.putOFStringArray(str);
+    return result;
 }
 
-
 FGPlanePosPatient::~FGPlanePosPatient()
 {
-  // nothing to do
+    // nothing to do
 }
index 70e650a41764800b149e65e3c1473a33d5d0abd0..1980fd8bcc9bd3d1fc27b20db0f076350d1dc517 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  */
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcdeftag.h"
-#include "dcmtk/dcmiod/iodutil.h"
 #include "dcmtk/dcmfg/fgplanposvol.h"
 #include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/dcmiod/iodutil.h"
 
 // Constructor
-FGPlanePositionVolume::FGPlanePositionVolume() :
-  FGBase(DcmFGTypes::EFG_PLANEPOSITIONVOLUME),
-  m_ImagePositionVolume(DCM_ImagePositionVolume)
+FGPlanePositionVolume::FGPlanePositionVolume()
+    : FGBase(DcmFGTypes::EFG_PLANEPOSITIONVOLUME)
+    , m_ImagePositionVolume(DCM_ImagePositionVolume)
 {
 }
 
-
 FGPlanePositionVolume::~FGPlanePositionVolume()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
 FGBase* FGPlanePositionVolume::clone() const
 {
-  FGPlanePositionVolume* copy = new FGPlanePositionVolume();
-  if (copy)
-  {
-    copy->m_ImagePositionVolume = this->m_ImagePositionVolume;
-  }
-  return copy;
+    FGPlanePositionVolume* copy = new FGPlanePositionVolume();
+    if (copy)
+    {
+        copy->m_ImagePositionVolume = this->m_ImagePositionVolume;
+    }
+    return copy;
 }
 
-
 void FGPlanePositionVolume::clearData()
 {
-  m_ImagePositionVolume.clear();
+    m_ImagePositionVolume.clear();
 }
 
-
 OFCondition FGPlanePositionVolume::check() const
 {
-  // Checks in read() and write() are sufficient for now
-  return EC_Normal;
+    // Checks in read() and write() are sufficient for now
+    return EC_Normal;
 }
 
-
 // --- get() functionality ---
 
-OFCondition FGPlanePositionVolume::getImagePositionVolume(Float64& value,
-                                                          const long unsigned int pos)
+OFCondition FGPlanePositionVolume::getImagePositionVolume(Float64& value, const long unsigned int pos)
 {
-  return m_ImagePositionVolume.getFloat64(value, pos);
+    return m_ImagePositionVolume.getFloat64(value, pos);
 }
 
-
-OFCondition FGPlanePositionVolume::getImagePositionVolume(Float64& valueX,
-                                                          Float64& valueY,
-                                                          Float64& valueZ)
+OFCondition FGPlanePositionVolume::getImagePositionVolume(Float64& valueX, Float64& valueY, Float64& valueZ)
 {
-  OFCondition result = m_ImagePositionVolume.getFloat64(valueX, 0);
-  if (result.good()) result = m_ImagePositionVolume.getFloat64(valueY, 1);
-  if (result.good()) result = m_ImagePositionVolume.getFloat64(valueZ, 2);
-  return result;
+    OFCondition result = m_ImagePositionVolume.getFloat64(valueX, 0);
+    if (result.good())
+        result = m_ImagePositionVolume.getFloat64(valueY, 1);
+    if (result.good())
+        result = m_ImagePositionVolume.getFloat64(valueZ, 2);
+    return result;
 }
 
-
 OFCondition FGPlanePositionVolume::setImagePositionVolume(const Float64& valueX,
                                                           const Float64& valueY,
                                                           const Float64& valueZ,
                                                           const OFBool checkValue)
 {
-  (void)checkValue;
-  OFCondition result = m_ImagePositionVolume.putFloat64(valueX, 0);
-  if (result.good()) result = m_ImagePositionVolume.putFloat64(valueY, 1);
-  if (result.good()) result = m_ImagePositionVolume.putFloat64(valueZ, 2);
-  return result;
+    (void)checkValue;
+    OFCondition result = m_ImagePositionVolume.putFloat64(valueX, 0);
+    if (result.good())
+        result = m_ImagePositionVolume.putFloat64(valueY, 1);
+    if (result.good())
+        result = m_ImagePositionVolume.putFloat64(valueZ, 2);
+    return result;
 }
 
-
 OFCondition FGPlanePositionVolume::setImagePositionVolume(const Float64& value,
                                                           const long unsigned int pos,
                                                           const OFBool checkValue)
 {
-  // no checks
-  (void)checkValue;
-  if (pos > 2)
-    return EC_ValueMultiplicityViolated;
+    // no checks
+    (void)checkValue;
+    if (pos > 2)
+        return EC_ValueMultiplicityViolated;
 
-  return m_ImagePositionVolume.putFloat64(value, pos);
+    return m_ImagePositionVolume.putFloat64(value, pos);
 }
 
-
 /// Read Plane Position (Volume) Sequence from given item
 OFCondition FGPlanePositionVolume::read(DcmItem& item)
 {
-  clearData();
-
-  DcmItem* seqItem = NULL;
-  OFCondition result = getItemFromFGSequence(item, DCM_PlanePositionVolumeSequence, 0, seqItem);
-  if (result.bad())
-    return result;
+    clearData();
 
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_ImagePositionVolume, "3", "1", "PlanePositionVolume");
+    DcmItem* seqItem   = NULL;
+    OFCondition result = getItemFromFGSequence(item, DCM_PlanePositionVolumeSequence, 0, seqItem);
+    if (result.bad())
+        return result;
 
-  return EC_Normal;
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_ImagePositionVolume, "3", "1", "PlanePositionVolume");
 
+    return EC_Normal;
 }
 
 /// Writes single Plane Position (Volume) Sequence into given item
 OFCondition FGPlanePositionVolume::write(DcmItem& item)
 {
-  DcmItem *seqItem = NULL;
-  OFCondition result = createNewFGSequence(item, DCM_PlanePositionVolumeSequence, 0, seqItem);
-  if (result.bad())
-    return result;
+    DcmItem* seqItem   = NULL;
+    OFCondition result = createNewFGSequence(item, DCM_PlanePositionVolumeSequence, 0, seqItem);
+    if (result.bad())
+        return result;
 
-  // --- write frame content macro attributes ---
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_ImagePositionVolume, "3", "1", "PlanePositionVolume");
-  return result;
+    // --- write frame content macro attributes ---
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_ImagePositionVolume, "3", "1", "PlanePositionVolume");
+    return result;
 }
 
-
 int FGPlanePositionVolume::compare(const FGBase& rhs) const
 {
-  int result = FGBase::compare(rhs);
-  if (result != 0)
-    return result;
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
 
-  const FGPlanePositionVolume* myRhs = OFstatic_cast(const FGPlanePositionVolume*, &rhs);
-  if (!myRhs)
-    return -1;
+    const FGPlanePositionVolume* myRhs = OFstatic_cast(const FGPlanePositionVolume*, &rhs);
+    if (!myRhs)
+        return -1;
 
-  // Compare all elements
-  result = m_ImagePositionVolume.compare(myRhs->m_ImagePositionVolume);
-  return result;
+    // Compare all elements
+    result = m_ImagePositionVolume.compare(myRhs->m_ImagePositionVolume);
+    return result;
 }
index b876b39bcd730787912b5d583c97e72d6979856b..e5e8b19b11703b6592618b6f0a9e0afcf3328d79 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  */
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmfg/fgrealworldvaluemapping.h"
+
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgrealworldvaluemapping.h"
 #include "dcmtk/dcmiod/iodutil.h"
 
 const OFString FGRealWorldValueMapping::RWVMItem::m_ModuleName = "RealWorldValueMappingItemMacro";
 
 FGRealWorldValueMapping::FGRealWorldValueMapping()
-: FGBase(DcmFGTypes::EFG_REALWORLDVALUEMAPPING),
-  m_Items()
+    : FGBase(DcmFGTypes::EFG_REALWORLDVALUEMAPPING)
+    , m_Items()
 {
 }
 
-
 FGRealWorldValueMapping::~FGRealWorldValueMapping()
 {
- clearData();
   clearData();
 }
 
-
 FGBase* FGRealWorldValueMapping::clone() const
 {
-  FGRealWorldValueMapping* copy = new FGRealWorldValueMapping();
-  if (copy)
-  {
-    for (OFVector<FGRealWorldValueMapping::RWVMItem*>::const_iterator it = m_Items.begin(); it < m_Items.end(); it++)
+    FGRealWorldValueMapping* copy = new FGRealWorldValueMapping();
+    if (copy)
     {
-      if (*it == NULL) return NULL;
-      FGRealWorldValueMapping::RWVMItem* item = (*it)->clone();
-      if (item == NULL) return NULL;
-      copy->m_Items.push_back(item);
+        for (OFVector<FGRealWorldValueMapping::RWVMItem*>::const_iterator it = m_Items.begin(); it < m_Items.end();
+             it++)
+        {
+            if (*it == NULL)
+                return NULL;
+            FGRealWorldValueMapping::RWVMItem* item = (*it)->clone();
+            if (item == NULL)
+                return NULL;
+            copy->m_Items.push_back(item);
+        }
     }
-  }
-  return copy;
+    return copy;
 }
 
-
 void FGRealWorldValueMapping::clearData()
 {
-  DcmIODUtil::freeContainer(m_Items);
+    DcmIODUtil::freeContainer(m_Items);
 }
 
-
 OFCondition FGRealWorldValueMapping::check() const
 {
-  // More checks checks for 1C conditions could be added
-  return EC_Normal;
+    // More checks checks for 1C conditions could be added
+    return EC_Normal;
 }
 
-
 int FGRealWorldValueMapping::compare(const FGBase& rhs) const
 {
-  int result = FGBase::compare(rhs);
-  if (result != 0)
-    return result;
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
 
-  const FGRealWorldValueMapping* myRhs = OFstatic_cast(const FGRealWorldValueMapping*, &rhs);
-  if (!myRhs)
-    return -1;
+    const FGRealWorldValueMapping* myRhs = OFstatic_cast(const FGRealWorldValueMapping*, &rhs);
+    if (!myRhs)
+        return -1;
 
-  // Compare all items, start with VM
-  if (m_Items.size() < myRhs->m_Items.size())
-    return 1;
-  else if (m_Items.size() > myRhs->m_Items.size())
-    return -1;
+    // Compare all items, start with VM
+    if (m_Items.size() < myRhs->m_Items.size())
+        return 1;
+    else if (m_Items.size() > myRhs->m_Items.size())
+        return -1;
 
-  for (size_t n = 0; m_Items.size(); n++)
-  {
-    result = m_Items[n]->compare( *(myRhs->m_Items[n]) );
-    if (result != 0) return result;
-  }
-  return result;
+    for (size_t n = 0; m_Items.size(); n++)
+    {
+        result = m_Items[n]->compare(*(myRhs->m_Items[n]));
+        if (result != 0)
+            return result;
+    }
+    return result;
 }
 
-
 /// Read from Frame Content Sequence
 OFCondition FGRealWorldValueMapping::read(DcmItem& item)
 {
-  clearData();
+    clearData();
 
-  DcmIODUtil::readSubSequence(item, DCM_RealWorldValueMappingSequence, m_Items, "1-n", "1", "RealWorldValueMappingMacro");
+    DcmIODUtil::readSubSequence(
+        item, DCM_RealWorldValueMappingSequence, m_Items, "1-n", "1", "RealWorldValueMappingMacro");
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
 OFCondition FGRealWorldValueMapping::write(DcmItem& item)
 {
-  // OFCondition result = createNewFGSequence(item, DCM_RealWorldValueMappingSequence, 0, seqItem);
-  OFCondition result;
-  DcmIODUtil::writeSubSequence(result,  DCM_RealWorldValueMappingSequence, m_Items, item, "1-n", "1", "RealWorldValueMappingMacro");
-  return result;
+    // OFCondition result = createNewFGSequence(item, DCM_RealWorldValueMappingSequence, 0, seqItem);
+    OFCondition result;
+    DcmIODUtil::writeSubSequence(
+        result, DCM_RealWorldValueMappingSequence, m_Items, item, "1-n", "1", "RealWorldValueMappingMacro");
+    return result;
 }
 
-
-OFVector< FGRealWorldValueMapping::RWVMItem* >& FGRealWorldValueMapping::getRealWorldValueMapping()
+OFVector<FGRealWorldValueMapping::RWVMItem*>& FGRealWorldValueMapping::getRealWorldValueMapping()
 {
-  return m_Items;
+    return m_Items;
 }
 
-
 // -----------------------------------------------------------
 
-
 FGRealWorldValueMapping::RWVMItem::RWVMItem(IODComponent* parent)
-: IODComponent(parent),
-  m_MeasurementUnitsCode(),
-  m_QuantityDefinitionSequence()
+    : IODComponent(parent)
+    , m_MeasurementUnitsCode()
+    , m_QuantityDefinitionSequence()
 {
-  resetRules();
+    resetRules();
 }
 
-
-FGRealWorldValueMapping::RWVMItem::RWVMItem(OFshared_ptr< DcmItem > item,
-                                            OFshared_ptr< IODRules > rules,
+FGRealWorldValueMapping::RWVMItem::RWVMItem(OFshared_ptr<DcmItem> item,
+                                            OFshared_ptr<IODRules> rules,
                                             IODComponent* parent)
-: IODComponent(item, rules, parent),
-  m_MeasurementUnitsCode(),
-  m_QuantityDefinitionSequence()
+    : IODComponent(item, rules, parent)
+    , m_MeasurementUnitsCode()
+    , m_QuantityDefinitionSequence()
 {
-  resetRules();
+    resetRules();
 }
 
-
 FGRealWorldValueMapping::RWVMItem::RWVMItem(const FGRealWorldValueMapping::RWVMItem& rhs)
-: IODComponent(rhs),
-  m_MeasurementUnitsCode(rhs.m_MeasurementUnitsCode),
-  m_QuantityDefinitionSequence()
-{
-  OFVector<ContentItemMacro*>::const_iterator it = rhs.m_QuantityDefinitionSequence.begin();
-  while (it != rhs.m_QuantityDefinitionSequence.end())
-  {
-    ContentItemMacro* macro = new ContentItemMacro(**it);
-    if (macro == NULL)
+    : IODComponent(rhs)
+    , m_MeasurementUnitsCode(rhs.m_MeasurementUnitsCode)
+    , m_QuantityDefinitionSequence()
+{
+    OFVector<ContentItemMacro*>::const_iterator it = rhs.m_QuantityDefinitionSequence.begin();
+    while (it != rhs.m_QuantityDefinitionSequence.end())
     {
-      DCMFG_ERROR("Out of memory in copy constructor of FGRealWorldValueMapping::RWVMItem::RWVMItem");
-      return;
+        ContentItemMacro* macro = new ContentItemMacro(**it);
+        if (macro == NULL)
+        {
+            DCMFG_ERROR("Out of memory in copy constructor of FGRealWorldValueMapping::RWVMItem::RWVMItem");
+            return;
+        }
+        m_QuantityDefinitionSequence.push_back(macro);
+        it++;
     }
-    m_QuantityDefinitionSequence.push_back(macro);
-    it++;
-  }
 }
 
-
-
 FGRealWorldValueMapping::RWVMItem* FGRealWorldValueMapping::RWVMItem::clone()
 {
-  return new FGRealWorldValueMapping::RWVMItem(*this);
+    return new FGRealWorldValueMapping::RWVMItem(*this);
 }
 
-
-
 FGRealWorldValueMapping::RWVMItem::~RWVMItem()
 {
-  DcmIODUtil::freeContainer(m_QuantityDefinitionSequence);
+    DcmIODUtil::freeContainer(m_QuantityDefinitionSequence);
 }
 
-
 OFString FGRealWorldValueMapping::RWVMItem::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 int FGRealWorldValueMapping::RWVMItem::compare(const IODComponent& rhs) const
 {
-  int result = IODComponent::compare(rhs);
-  const FGRealWorldValueMapping::RWVMItem* myRhs = OFstatic_cast(const FGRealWorldValueMapping::RWVMItem*, &rhs);
-  if (!myRhs)
-    return -1;
-
-  if (result == 0) result = m_MeasurementUnitsCode.compare(*myRhs);
-  if (result == 0)
-  {
-    size_t rhsSize = myRhs->m_QuantityDefinitionSequence.size();
-    size_t thisSize = m_QuantityDefinitionSequence.size();
-    if (thisSize < rhsSize)
-      return -1;
-    else if (thisSize > rhsSize)
-      return 1;
-
-    OFVector<ContentItemMacro*>::const_iterator it = m_QuantityDefinitionSequence.begin();
-    OFVector<ContentItemMacro*>::const_iterator rhsIt = myRhs->m_QuantityDefinitionSequence.begin();
-    while (it != m_QuantityDefinitionSequence.end() && (result == 0))
+    int result                                     = IODComponent::compare(rhs);
+    const FGRealWorldValueMapping::RWVMItem* myRhs = OFstatic_cast(const FGRealWorldValueMapping::RWVMItem*, &rhs);
+    if (!myRhs)
+        return -1;
+
+    if (result == 0)
+        result = m_MeasurementUnitsCode.compare(*myRhs);
+    if (result == 0)
     {
-        result = (*it)->compare( *(*rhsIt) );
-        it++;
+        size_t rhsSize  = myRhs->m_QuantityDefinitionSequence.size();
+        size_t thisSize = m_QuantityDefinitionSequence.size();
+        if (thisSize < rhsSize)
+            return -1;
+        else if (thisSize > rhsSize)
+            return 1;
+
+        OFVector<ContentItemMacro*>::const_iterator it    = m_QuantityDefinitionSequence.begin();
+        OFVector<ContentItemMacro*>::const_iterator rhsIt = myRhs->m_QuantityDefinitionSequence.begin();
+        while (it != m_QuantityDefinitionSequence.end() && (result == 0))
+        {
+            result = (*it)->compare(*(*rhsIt));
+            it++;
+        }
     }
-  }
-  return result;
-
+    return result;
 }
 
-
 void FGRealWorldValueMapping::RWVMItem::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_RealWorldValueFirstValueMapped, "1","1C",getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_RealWorldValueLastValueMapped, "1","1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_DoubleFloatRealWorldValueFirstValueMapped, "1","1C",getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_DoubleFloatRealWorldValueLastValueMapped, "1","1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_RealWorldValueIntercept, "1","1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_RealWorldValueSlope, "1","1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_RealWorldValueLUTData, "1-n","1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_LUTExplanation, "1","1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_LUTLabel, "1","1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_MeasurementUnitsCodeSequence, "1","1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_QuantityDefinitionSequence, "1-n","3", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_RealWorldValueFirstValueMapped, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_RealWorldValueLastValueMapped, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE),
+                     OFTrue);
+    m_Rules->addRule(
+        new IODRule(DCM_DoubleFloatRealWorldValueFirstValueMapped, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE),
+        OFTrue);
+    m_Rules->addRule(
+        new IODRule(DCM_DoubleFloatRealWorldValueLastValueMapped, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE),
+        OFTrue);
+    m_Rules->addRule(new IODRule(DCM_RealWorldValueIntercept, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_RealWorldValueSlope, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_RealWorldValueLUTData, "1-n", "1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_LUTExplanation, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_LUTLabel, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_MeasurementUnitsCodeSequence, "1", "1", getName(), DcmIODTypes::IE_INSTANCE),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_QuantityDefinitionSequence, "1-n", "3", getName(), DcmIODTypes::IE_INSTANCE),
+                     OFTrue);
+}
+
+OFCondition FGRealWorldValueMapping::RWVMItem::read(DcmItem& source, const OFBool clearOldData)
+{
+    DcmIODUtil::readSingleItem(source, DCM_MeasurementUnitsCodeSequence, m_MeasurementUnitsCode, "1", m_ModuleName);
+    DcmIODUtil::readSubSequence(source,
+                                DCM_QuantityDefinitionSequence,
+                                m_QuantityDefinitionSequence,
+                                m_Rules->getByTag(DCM_QuantityDefinitionSequence));
+    return IODComponent::read(source, clearOldData);
 }
 
-
-OFCondition FGRealWorldValueMapping::RWVMItem::read(DcmItem& source,
-                                                    const OFBool clearOldData)
-{
-  DcmIODUtil::readSingleItem(source, DCM_MeasurementUnitsCodeSequence, m_MeasurementUnitsCode, "1", m_ModuleName);
-  DcmIODUtil::readSubSequence(source, DCM_QuantityDefinitionSequence, m_QuantityDefinitionSequence, m_Rules->getByTag(DCM_QuantityDefinitionSequence));
-  return IODComponent::read(source, clearOldData);
-}
-
-
 OFCondition FGRealWorldValueMapping::RWVMItem::write(DcmItem& destination)
 {
-  OFCondition result;
-  DcmIODUtil::writeSingleItem(result, DCM_MeasurementUnitsCodeSequence, m_MeasurementUnitsCode, *m_Item, "1", m_ModuleName);
-  DcmIODUtil::writeSubSequence(result, DCM_QuantityDefinitionSequence, m_QuantityDefinitionSequence, *m_Item, m_Rules->getByTag(DCM_QuantityDefinitionSequence));
-  if (result.good()) result = IODComponent::write(destination);
-  return result;
+    OFCondition result;
+    DcmIODUtil::writeSingleItem(
+        result, DCM_MeasurementUnitsCodeSequence, m_MeasurementUnitsCode, *m_Item, "1", m_ModuleName);
+    DcmIODUtil::writeSubSequence(result,
+                                 DCM_QuantityDefinitionSequence,
+                                 m_QuantityDefinitionSequence,
+                                 *m_Item,
+                                 m_Rules->getByTag(DCM_QuantityDefinitionSequence));
+    if (result.good())
+        result = IODComponent::write(destination);
+    return result;
 }
 
-
 OFCondition FGRealWorldValueMapping::RWVMItem::getRealWorldValueFirstValueMapped(Sint32& value,
                                                                                  const unsigned long pos) const
 {
-  return getUSorSS(*m_Item, DCM_RealWorldValueFirstValueMapped, pos, value);
+    return getUSorSS(*m_Item, DCM_RealWorldValueFirstValueMapped, pos, value);
 }
 
-
 OFCondition FGRealWorldValueMapping::RWVMItem::getRealWorldValueLastValueMapped(Sint32& value,
                                                                                 const unsigned long pos) const
 {
-  return getUSorSS(*m_Item, DCM_RealWorldValueLastValueMapped, pos, value);
+    return getUSorSS(*m_Item, DCM_RealWorldValueLastValueMapped, pos, value);
 }
 
-
-OFCondition FGRealWorldValueMapping::RWVMItem::getDoubleFloatRealWorldValueFirstValueMapped(Float64& value,
-                                                                                            const unsigned long pos) const
+OFCondition
+FGRealWorldValueMapping::RWVMItem::getDoubleFloatRealWorldValueFirstValueMapped(Float64& value,
+                                                                                const unsigned long pos) const
 {
-  return (*m_Item).findAndGetFloat64(DCM_DoubleFloatRealWorldValueFirstValueMapped, value, pos);
+    return (*m_Item).findAndGetFloat64(DCM_DoubleFloatRealWorldValueFirstValueMapped, value, pos);
 }
 
-
-OFCondition FGRealWorldValueMapping::RWVMItem::getDoubleFloatRealWorldValueLastValueMapped(Float64& value,
-                                                                                           const unsigned long pos) const
+OFCondition
+FGRealWorldValueMapping::RWVMItem::getDoubleFloatRealWorldValueLastValueMapped(Float64& value,
+                                                                               const unsigned long pos) const
 {
-  return (*m_Item).findAndGetFloat64(DCM_DoubleFloatRealWorldValueFirstValueMapped, value, pos);
+    return (*m_Item).findAndGetFloat64(DCM_DoubleFloatRealWorldValueFirstValueMapped, value, pos);
 }
 
-
-OFCondition FGRealWorldValueMapping::RWVMItem::getRealWorldValueLUTData(OFVector< Float64 >& values) const
+OFCondition FGRealWorldValueMapping::RWVMItem::getRealWorldValueLUTData(OFVector<Float64>& values) const
 {
-  DcmElement* elem = NULL;
-  OFCondition result = m_Item->findAndGetElement(DCM_RealWorldValueLUTData, elem);
-  if (result.good())
-  {
-    size_t numValues = elem->getNumberOfValues();
-    for (size_t n = 0; n < numValues; n++)
+    DcmElement* elem   = NULL;
+    OFCondition result = m_Item->findAndGetElement(DCM_RealWorldValueLUTData, elem);
+    if (result.good())
     {
-      Float64 value;
-      result = elem->getFloat64(value, OFstatic_cast(unsigned long, n));
-      if (result.good()) values.push_back(value);
+        size_t numValues = elem->getNumberOfValues();
+        for (size_t n = 0; n < numValues; n++)
+        {
+            Float64 value;
+            result = elem->getFloat64(value, OFstatic_cast(unsigned long, n));
+            if (result.good())
+                values.push_back(value);
+        }
     }
-  }
-  return result;
+    return result;
 }
 
-
-OFCondition FGRealWorldValueMapping::RWVMItem::getRealWorldValueLUTData(Float64& value,
-                                                                        const unsigned long pos) const
+OFCondition FGRealWorldValueMapping::RWVMItem::getRealWorldValueLUTData(Float64& value, const unsigned long pos) const
 {
-  return m_Item->findAndGetFloat64(DCM_RealWorldValueLUTData, value, pos);
+    return m_Item->findAndGetFloat64(DCM_RealWorldValueLUTData, value, pos);
 }
 
-
-OFCondition FGRealWorldValueMapping::RWVMItem::getLUTExplanation(OFString& value,
-                                                                 const signed long pos) const
+OFCondition FGRealWorldValueMapping::RWVMItem::getLUTExplanation(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_LUTExplanation, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_LUTExplanation, *m_Item, value, pos);
 }
 
-
-OFCondition FGRealWorldValueMapping::RWVMItem::getLUTLabel(OFString& value,
-                                                           const signed long pos) const
+OFCondition FGRealWorldValueMapping::RWVMItem::getLUTLabel(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_LUTLabel, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_LUTLabel, *m_Item, value, pos);
 }
 
-
 CodeSequenceMacro& FGRealWorldValueMapping::RWVMItem::getMeasurementUnitsCode()
 {
-  return m_MeasurementUnitsCode;
+    return m_MeasurementUnitsCode;
 }
 
-
-OFVector<ContentItemMacro*> & FGRealWorldValueMapping::RWVMItem::getEntireQuantityDefinitionSequence()
+OFVector<ContentItemMacro*>& FGRealWorldValueMapping::RWVMItem::getEntireQuantityDefinitionSequence()
 {
-  return m_QuantityDefinitionSequence;
+    return m_QuantityDefinitionSequence;
 }
 
-
 OFCondition FGRealWorldValueMapping::RWVMItem::setRealWorldValueFirstValueMappedUnsigned(const Uint16 value,
                                                                                          const OFBool checkValue)
 {
-  (void)checkValue;
-  DcmUnsignedShort* us = new DcmUnsignedShort(DCM_RealWorldValueFirstValueMapped);
-  OFCondition result = us->putUint16(value);
-  if (result.good()) result = m_Item->insert(us, OFTrue /* replace old */);
-  if (result.bad()) delete us;
-  return result;
+    (void)checkValue;
+    DcmUnsignedShort* us = new DcmUnsignedShort(DCM_RealWorldValueFirstValueMapped);
+    OFCondition result   = us->putUint16(value);
+    if (result.good())
+        result = m_Item->insert(us, OFTrue /* replace old */);
+    if (result.bad())
+        delete us;
+    return result;
 }
 
-
 OFCondition FGRealWorldValueMapping::RWVMItem::setRealWorldValueFirstValueMappedSigned(const Sint16& value,
                                                                                        const OFBool checkValue)
 {
-  (void)checkValue;
-  DcmSignedShort* ss = new DcmSignedShort(DCM_RealWorldValueFirstValueMapped);
-  OFCondition result = ss->putSint16(value);
-  if (result.good()) result = m_Item->insert(ss, OFTrue /* replace old */);
-  if (result.bad()) delete ss;
-  return result;
+    (void)checkValue;
+    DcmSignedShort* ss = new DcmSignedShort(DCM_RealWorldValueFirstValueMapped);
+    OFCondition result = ss->putSint16(value);
+    if (result.good())
+        result = m_Item->insert(ss, OFTrue /* replace old */);
+    if (result.bad())
+        delete ss;
+    return result;
 }
 
 OFCondition FGRealWorldValueMapping::RWVMItem::setRealWorldValueLastValueMappedSigned(const Sint16& value,
                                                                                       const OFBool checkValue)
 {
-  (void)checkValue;
-  DcmSignedShort* ss = new DcmSignedShort(DCM_RealWorldValueLastValueMapped);
-  OFCondition result = ss->putSint16(value);
-  if (result.good()) result = m_Item->insert(ss, OFTrue /* replace old */);
-  if (result.bad()) delete ss;
-  return result;
-
+    (void)checkValue;
+    DcmSignedShort* ss = new DcmSignedShort(DCM_RealWorldValueLastValueMapped);
+    OFCondition result = ss->putSint16(value);
+    if (result.good())
+        result = m_Item->insert(ss, OFTrue /* replace old */);
+    if (result.bad())
+        delete ss;
+    return result;
 }
 
-
 OFCondition FGRealWorldValueMapping::RWVMItem::setRealWorldValueLastValueMappedUnsigned(const Uint16 value,
                                                                                         const OFBool checkValue)
 {
-  (void)checkValue;
-  DcmUnsignedShort* us = new DcmUnsignedShort(DCM_RealWorldValueLastValueMapped);
-  OFCondition result = us->putUint16(value);
-  if (result.good()) result = m_Item->insert(us, OFTrue /* replace old */);
-  if (result.bad()) delete us;
-  return result;
+    (void)checkValue;
+    DcmUnsignedShort* us = new DcmUnsignedShort(DCM_RealWorldValueLastValueMapped);
+    OFCondition result   = us->putUint16(value);
+    if (result.good())
+        result = m_Item->insert(us, OFTrue /* replace old */);
+    if (result.bad())
+        delete us;
+    return result;
 }
 
-
 OFCondition FGRealWorldValueMapping::RWVMItem::setDoubleFloatRealWorldValueFirstValueMapped(const Float64 value,
                                                                                             const OFBool checkValue)
 {
-  (void)checkValue;
-  return (*m_Item).putAndInsertFloat64(DCM_DoubleFloatRealWorldValueFirstValueMapped, value);
+    (void)checkValue;
+    return (*m_Item).putAndInsertFloat64(DCM_DoubleFloatRealWorldValueFirstValueMapped, value);
 }
 
-
 OFCondition FGRealWorldValueMapping::RWVMItem::setDoubleFloatRealWorldValueLastValueMapped(const Float64 value,
                                                                                            const OFBool checkValue)
 {
-  (void)checkValue;
-  return (*m_Item).putAndInsertFloat64(DCM_DoubleFloatRealWorldValueLastValueMapped, value);
+    (void)checkValue;
+    return (*m_Item).putAndInsertFloat64(DCM_DoubleFloatRealWorldValueLastValueMapped, value);
 }
 
-
-OFCondition FGRealWorldValueMapping::RWVMItem::setRealWorldValueIntercept(const Float64 value,
-                                                                          const OFBool checkValue)
+OFCondition FGRealWorldValueMapping::RWVMItem::setRealWorldValueIntercept(const Float64 value, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertFloat64(DCM_RealWorldValueIntercept, value);
+    (void)checkValue;
+    return m_Item->putAndInsertFloat64(DCM_RealWorldValueIntercept, value);
 }
 
-
-OFCondition FGRealWorldValueMapping::RWVMItem::setRealWorldValueSlope(const Float64 value,
-                                                                      const OFBool checkValue)
+OFCondition FGRealWorldValueMapping::RWVMItem::setRealWorldValueSlope(const Float64 value, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertFloat64(DCM_RealWorldValueSlope, value);
+    (void)checkValue;
+    return m_Item->putAndInsertFloat64(DCM_RealWorldValueSlope, value);
 }
 
-
-OFCondition FGRealWorldValueMapping::RWVMItem::setRealWorldValueLUTData(const OFVector< Float64 >& value,
+OFCondition FGRealWorldValueMapping::RWVMItem::setRealWorldValueLUTData(const OFVector<Float64>& value,
                                                                         const OFBool checkValue)
 {
-  (void)checkValue;
-  DcmElement *elem = NULL;
-  OFCondition result = m_Item->findAndGetElement(DCM_RealWorldValueLUTData, elem);
-  if (result.good())
-  {
-    size_t count = value.size();
-    for (size_t n = 0; n < count; n++)
+    (void)checkValue;
+    DcmElement* elem   = NULL;
+    OFCondition result = m_Item->findAndGetElement(DCM_RealWorldValueLUTData, elem);
+    if (result.good())
     {
-      if (result.good()) result = elem->putFloat64(value[n], OFstatic_cast(unsigned long, n));
+        size_t count = value.size();
+        for (size_t n = 0; n < count; n++)
+        {
+            if (result.good())
+                result = elem->putFloat64(value[n], OFstatic_cast(unsigned long, n));
+        }
     }
-  }
-  return result;
+    return result;
 }
 
-
-OFCondition FGRealWorldValueMapping::RWVMItem::setLUTExplanation(const OFString& value,
-                                                                 const OFBool checkValue)
+OFCondition FGRealWorldValueMapping::RWVMItem::setLUTExplanation(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_LUTExplanation, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_LUTExplanation, value);
+    return result;
 }
 
-
-OFCondition FGRealWorldValueMapping::RWVMItem::setLUTLabel(const OFString& value,
-                                                           const OFBool checkValue)
+OFCondition FGRealWorldValueMapping::RWVMItem::setLUTLabel(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_LUTLabel, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_LUTLabel, value);
+    return result;
 }
 
-
 OFCondition FGRealWorldValueMapping::RWVMItem::getUSorSS(DcmItem& item,
                                                          const DcmTagKey& key,
                                                          const unsigned long pos,
                                                          Sint32& value)
 {
-  DcmElement *elem = NULL;
-  OFCondition result = item.findAndGetElement(key, elem);
-  if (result.good() && elem)
-  {
-    DcmEVR evr = elem->getVR();
-    if (evr == EVR_US)
+    DcmElement* elem   = NULL;
+    OFCondition result = item.findAndGetElement(key, elem);
+    if (result.good() && elem)
     {
-      Uint16 num;
-      result = elem->getUint16(num, pos);
-      if (result.good()) value = num;
+        DcmEVR evr = elem->getVR();
+        if (evr == EVR_US)
+        {
+            Uint16 num;
+            result = elem->getUint16(num, pos);
+            if (result.good())
+                value = num;
+        }
+        else if (evr == EVR_SS)
+        {
+            Sint16 num;
+            result = elem->getSint16(num, pos);
+            if (result.good())
+                value = num;
+        }
+        else
+        {
+            DCMFG_ERROR("Illegal VR " << DcmVR(evr).getVRName() << " for tag " << DcmTag(key).getTagName());
+            result = EC_InvalidVR;
+        }
     }
-    else if (evr == EVR_SS)
-    {
-      Sint16 num;
-      result = elem->getSint16(num, pos);
-      if (result.good()) value = num;
-    }
-    else
-    {
-      DCMFG_ERROR("Illegal VR " << DcmVR(evr).getVRName() << " for tag " << DcmTag(key).getTagName());
-      result = EC_InvalidVR;
-    }
-  }
-  return result;
+    return result;
 }
index 998501072b5b42f83201fc163255f2440c6d5ee8..71b44edd11f6fe9dd7e7a342b490a6f0152f09bd 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  */
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmfg/fgseg.h"
+
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgseg.h"
 #include "dcmtk/dcmiod/iodutil.h" // for static element helpers
 
-
-FGSegmentation::FGSegmentation() :
-  FGBase(DcmFGTypes::EFG_SEGMENTATION),
-  m_ReferencedSegmentNumber(DCM_ReferencedSegmentNumber)
+FGSegmentation::FGSegmentation()
+    : FGBase(DcmFGTypes::EFG_SEGMENTATION)
+    , m_ReferencedSegmentNumber(DCM_ReferencedSegmentNumber)
 {
 }
 
-
 FGSegmentation::~FGSegmentation()
 {
-  clearData();
+    clearData();
 }
 
 FGBase* FGSegmentation::clone() const
 {
-  FGSegmentation* copy = new FGSegmentation();
-  if (copy)
-  {
-    copy->m_ReferencedSegmentNumber = this->m_ReferencedSegmentNumber;
-  }
-  return copy;
+    FGSegmentation* copy = new FGSegmentation();
+    if (copy)
+    {
+        copy->m_ReferencedSegmentNumber = this->m_ReferencedSegmentNumber;
+    }
+    return copy;
 }
 
-
-
 void FGSegmentation::clearData()
 {
-  m_ReferencedSegmentNumber.clear();
+    m_ReferencedSegmentNumber.clear();
 }
 
-
 OFCondition FGSegmentation::check() const
 {
-  // Checks in read() and write() are sufficient for now
-  return EC_Normal;
+    // Checks in read() and write() are sufficient for now
+    return EC_Normal;
 }
 
-
-OFCondition FGSegmentation::getReferencedSegmentNumber(Uint16& value,
-                                                       const unsigned long pos)
+OFCondition FGSegmentation::getReferencedSegmentNumber(Uint16& value, const unsigned long pos)
 {
-  return m_ReferencedSegmentNumber.getUint16(value, pos);
+    return m_ReferencedSegmentNumber.getUint16(value, pos);
 }
 
-
 OFCondition FGSegmentation::setReferencedSegmentNumber(const Uint16& segmentNumber)
 {
-  return m_ReferencedSegmentNumber.putUint16(segmentNumber);
+    return m_ReferencedSegmentNumber.putUint16(segmentNumber);
 }
 
-
 OFCondition FGSegmentation::write(DcmItem& item)
 {
-  OFCondition result = EC_Normal;
-
-  /* Clear old data */
-  item.findAndDeleteElement(DCM_SegmentIdentificationSequence);
-
-  /* write and get Segment Identification Sequence with one item */
-  DcmItem *newItem = NULL;
-  result = item.findOrCreateSequenceItem(DCM_SegmentIdentificationSequence, newItem, 0);
-  if ( result.bad() )
-  {
-    DCMFG_ERROR("Could not create Segment Identification Sequence with one item (internal error): " << result.text());
-    return FG_EC_CouldNotWriteFG;
-  }
-  DcmIODUtil::copyElementToDataset(result, *newItem, m_ReferencedSegmentNumber, "1-n", "1", "SegmentationMacro");
-
-  /* Return result */
-  return result;
-}
+    OFCondition result = EC_Normal;
+
+    /* Clear old data */
+    item.findAndDeleteElement(DCM_SegmentIdentificationSequence);
+
+    /* write and get Segment Identification Sequence with one item */
+    DcmItem* newItem = NULL;
+    result           = item.findOrCreateSequenceItem(DCM_SegmentIdentificationSequence, newItem, 0);
+    if (result.bad())
+    {
+        DCMFG_ERROR(
+            "Could not create Segment Identification Sequence with one item (internal error): " << result.text());
+        return FG_EC_CouldNotWriteFG;
+    }
+    DcmIODUtil::copyElementToDataset(result, *newItem, m_ReferencedSegmentNumber, "1-n", "1", "SegmentationMacro");
 
+    /* Return result */
+    return result;
+}
 
 OFCondition FGSegmentation::read(DcmItem& item)
 {
-  OFCondition result = EC_Normal;
+    OFCondition result = EC_Normal;
 
-  /* re-initialize object */
-  clearData();
+    /* re-initialize object */
+    clearData();
 
-  DcmSequenceOfItems *segmentIdentificationSequence = NULL;
-  result = item.findAndGetSequence(DCM_SegmentIdentificationSequence, segmentIdentificationSequence);
+    DcmSequenceOfItems* segmentIdentificationSequence = NULL;
+    result = item.findAndGetSequence(DCM_SegmentIdentificationSequence, segmentIdentificationSequence);
 
-  if ( result.good() )
-  {
-    /* Referenced Segment Number */
-    // check whether structure is ok (single item in sequence) and report problems
-    DcmItem *idItem= NULL;
-    DcmIODUtil::getAndCheckSingleItem(*segmentIdentificationSequence, idItem, DCM_SegmentIdentificationSequence);
-    if (idItem)
+    if (result.good())
     {
-      // so far we ignore the result when reading (but report problems to the logger)
-      DcmIODUtil::getAndCheckElementFromDataset(*idItem, m_ReferencedSegmentNumber, "1-n" /* vm */, "1" /* type */, "SegmentationMacro");
+        /* Referenced Segment Number */
+        // check whether structure is ok (single item in sequence) and report problems
+        DcmItem* idItem = NULL;
+        DcmIODUtil::getAndCheckSingleItem(*segmentIdentificationSequence, idItem, DCM_SegmentIdentificationSequence);
+        if (idItem)
+        {
+            // so far we ignore the result when reading (but report problems to the logger)
+            DcmIODUtil::getAndCheckElementFromDataset(
+                *idItem, m_ReferencedSegmentNumber, "1-n" /* vm */, "1" /* type */, "SegmentationMacro");
+        }
     }
-  }
-  return result;
+    return result;
 }
 
-
 int FGSegmentation::compare(const FGBase& rhs) const
 {
-  int result = FGBase::compare(rhs);
-  if (result == 0)
-  {
-    const FGSegmentation* myRhs = OFstatic_cast(const FGSegmentation*, &rhs);
-    if (!myRhs)
-      return -1;
-
-    // Compare all elements
-    result = m_ReferencedSegmentNumber.compare(myRhs->m_ReferencedSegmentNumber);
-  }
-
-  return result;
+    int result = FGBase::compare(rhs);
+    if (result == 0)
+    {
+        const FGSegmentation* myRhs = OFstatic_cast(const FGSegmentation*, &rhs);
+        if (!myRhs)
+            return -1;
+
+        // Compare all elements
+        result = m_ReferencedSegmentNumber.compare(myRhs->m_ReferencedSegmentNumber);
+    }
+
+    return result;
 }
diff --git a/dcmfg/libsrc/fgtemporalposition.cc b/dcmfg/libsrc/fgtemporalposition.cc
new file mode 100644 (file)
index 0000000..27a4a75
--- /dev/null
@@ -0,0 +1,114 @@
+/*
+ *
+ *  Copyright (C) 2019, Open Connections GmbH
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmfg
+ *
+ *  Author: Michael Onken
+ *
+ *  Purpose: Class for managing the Temporal Position
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmfg/fgtemporalposition.h"
+#include "dcmtk/dcmiod/iodutil.h"
+
+FGTemporalPosition::FGTemporalPosition()
+    : FGBase(DcmFGTypes::EFG_TEMPORALPOSITION)
+    , m_TemporalPositionTimeOffset(DCM_TemporalPositionTimeOffset)
+{
+}
+
+FGTemporalPosition::~FGTemporalPosition()
+{
+}
+
+void FGTemporalPosition::clearData()
+{
+    m_TemporalPositionTimeOffset.clear();
+}
+
+OFCondition FGTemporalPosition::check() const
+{
+    return EC_Normal;
+}
+
+FGBase* FGTemporalPosition::clone() const
+{
+    if (FGTemporalPosition* copy = new FGTemporalPosition)
+    {
+        copy->m_TemporalPositionTimeOffset = m_TemporalPositionTimeOffset;
+        return copy;
+    }
+    return OFnullptr;
+}
+
+OFCondition FGTemporalPosition::read(DcmItem& item)
+{
+    clearData();
+
+    DcmItem* seqItem;
+    OFCondition result;
+
+    seqItem = OFnullptr;
+    result  = getItemFromFGSequence(item, DCM_TemporalPositionSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_TemporalPositionTimeOffset, "1", "1", "Temporal Position");
+
+    return EC_Normal;
+}
+
+OFCondition FGTemporalPosition::write(DcmItem& item)
+{
+    DcmItem* seqItem;
+    OFCondition result = check();
+    if (result.bad())
+        return result;
+
+    seqItem = OFnullptr;
+    result  = createNewFGSequence(item, DCM_TemporalPositionSequence, 0, seqItem);
+    if (result.bad())
+        return result;
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_TemporalPositionTimeOffset, "1", "1", "Temporal Position");
+
+    return result;
+}
+
+int FGTemporalPosition::compare(const FGBase& rhs) const
+{
+    int result = FGBase::compare(rhs);
+    if (result == 0)
+    {
+        const FGTemporalPosition* myRhs = OFstatic_cast(const FGTemporalPosition*, &rhs);
+
+        // Compare all elements
+        result = m_TemporalPositionTimeOffset.compare(myRhs->m_TemporalPositionTimeOffset);
+    }
+
+    return result;
+}
+
+OFCondition FGTemporalPosition::getTemporalPositionTimeOffset(Float64& value, const unsigned long pos) const
+{
+    return DcmIODUtil::getFloat64ValueFromElement(m_TemporalPositionTimeOffset, value, pos);
+}
+
+OFCondition FGTemporalPosition::setTemporalPositionTimeOffset(const Float64& value, const OFBool checkValue)
+{
+    // Maybe add checks later.
+    (void)checkValue;
+    return m_TemporalPositionTimeOffset.putFloat64(value);
+}
index 9fd723118a631739264d1ebd694d7b08e5709c75..0ff72e4f048053286be5684a1ee439731569c64b 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2017, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  */
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmfg/fgtypes.h"
+
 #include "dcmtk/dcmdata/dcerror.h"
-#include "dcmtk/dcmfg/fgdefine.h"
 #include "dcmtk/dcmfg/fgbase.h"
+#include "dcmtk/dcmfg/fgdefine.h"
+#include "dcmtk/dcmfg/fgtypes.h"
 #include "dcmtk/dcmiod/iodcommn.h"
 
 OFLogger DCM_dcmfgLogger = OFLog::getLogger("dcmtk.dcmfg");
@@ -32,156 +33,274 @@ OFLogger DCM_dcmfgLogger = OFLog::getLogger("dcmtk.dcmfg");
  *  constant definitions
  *---------------------------------*/
 
-// conditions
-makeOFConditionConst(FG_EC_DoubledFG,               OFM_dcmfg,  1, OF_error, "Doubled Functional Group");
-makeOFConditionConst(FG_EC_NoSuchGroup,             OFM_dcmfg,  2, OF_error, "No such Functional Group");
-makeOFConditionConst(FG_EC_NotEnoughItems,          OFM_dcmfg,  3, OF_error, "Not enough Items in Functional Group");
-makeOFConditionConst(FG_EC_TooManyItems,            OFM_dcmfg,  4, OF_error, "Too many Items in Functional Group");
-makeOFConditionConst(FG_EC_InvalidData,             OFM_dcmfg,  5, OF_error, "Invalid data in Functional Group");
-makeOFConditionConst(FG_EC_CouldNotWriteFG,         OFM_dcmfg,  6, OF_error, "Could not write Functional Group");
-makeOFConditionConst(FG_EC_CouldNotInsertFG,        OFM_dcmfg,  7, OF_error, "Could not insert Functional Group");
-makeOFConditionConst(FG_EC_NoSharedFG,              OFM_dcmfg,  8, OF_error, "No shared Functional Groups found");
-makeOFConditionConst(FG_EC_NoPerFrameFG,            OFM_dcmfg,  9, OF_error, "No Per-Frame Functional Groups found");
-makeOFConditionConst(FG_EC_CouldNotCreateFG,        OFM_dcmfg, 10, OF_error, "Could not create Functional Group");
+// Error Conditions
+makeOFConditionConst(FG_EC_DoubledFG, OFM_dcmfg, 1, OF_error, "Doubled Functional Group");
+makeOFConditionConst(FG_EC_NoSuchGroup, OFM_dcmfg, 2, OF_error, "No such Functional Group");
+makeOFConditionConst(FG_EC_NotEnoughItems, OFM_dcmfg, 3, OF_error, "Not enough Items in Functional Group");
+makeOFConditionConst(FG_EC_TooManyItems, OFM_dcmfg, 4, OF_error, "Too many Items in Functional Group");
+makeOFConditionConst(FG_EC_InvalidData, OFM_dcmfg, 5, OF_error, "Invalid data in Functional Group");
+makeOFConditionConst(FG_EC_CouldNotWriteFG, OFM_dcmfg, 6, OF_error, "Could not write Functional Group");
+makeOFConditionConst(FG_EC_CouldNotInsertFG, OFM_dcmfg, 7, OF_error, "Could not insert Functional Group");
+makeOFConditionConst(FG_EC_NoSharedFG, OFM_dcmfg, 8, OF_error, "No shared Functional Groups found");
+makeOFConditionConst(FG_EC_NoPerFrameFG, OFM_dcmfg, 9, OF_error, "No Per-Frame Functional Groups found");
+makeOFConditionConst(FG_EC_CouldNotCreateFG, OFM_dcmfg, 10, OF_error, "Could not create Functional Group");
 makeOFConditionConst(FG_EC_CouldNotReadSourceImage, OFM_dcmfg, 11, OF_error, "Could not read source image");
-makeOFConditionConst(FG_EC_CouldNotAddFG,           OFM_dcmfg, 12, OF_error, "Could add Functional Group");
-makeOFConditionConst(FG_EC_NotEnoughFrames,         OFM_dcmfg, 13, OF_error, "Not enough frames");
-makeOFConditionConst(FG_EC_NoStacksFound,           OFM_dcmfg, 14, OF_error, "No stacks found");
-
+makeOFConditionConst(FG_EC_CouldNotAddFG, OFM_dcmfg, 12, OF_error, "Could add Functional Group");
+makeOFConditionConst(FG_EC_NotEnoughFrames, OFM_dcmfg, 13, OF_error, "Not enough frames");
+makeOFConditionConst(FG_EC_NoStacksFound, OFM_dcmfg, 14, OF_error, "No stacks found");
+makeOFConditionConst(FG_EC_SOPClassForbidsConcatenations, OFM_dcmfg, 15, OF_error, "SOP Class forbids Concatenations");
+makeOFConditionConst(FG_EC_PixelDataMissing, OFM_dcmfg, 16, OF_error, "Pixel Data is missing");
+makeOFConditionConst(FG_EC_PixelDataDimensionsInvalid, OFM_dcmfg, 17, OF_error, "Pixel Data dimensions invalid");
+makeOFConditionConst(FG_EC_PixelDataTooLarge, OFM_dcmfg, 18, OF_error, "Pixel Data too large");
+makeOFConditionConst(FG_EC_InconsistentConcatenationData, OFM_dcmfg, 19, OF_error, "Inconsistent Concatenation Data");
+makeOFConditionConst(FG_EC_ConcatenationComplete, OFM_dcmfg, 20, OF_error, "Concatenation Complete - no more data");
+makeOFConditionConst(FG_EC_UnsupportedPixelDataLayout, OFM_dcmfg, 21, OF_error, "Unsupported pixel data layout");
 
 OFString DcmFGTypes::FGType2OFString(const DcmFGTypes::E_FGType fgType)
 {
-  switch (fgType)
-  {
-    /// Undefined functional group
-    case EFG_UNDEFINED: return "Undefined Functional Group Macro"; break;
-    /// Unknown functional group
-    case EFG_UNKNOWN: return "Unknown Functional Group Macro"; break;
-    /// Pixel Measures
-    case EFG_PIXELMEASURES: return "Pixel Measures Functional Group Macro"; break;
-    /// Frame Content
-    case EFG_FRAMECONTENT: return "Frame Content Functional Group Macro"; break;
-    /// Plane Position (Patient)
-    case EFG_PLANEPOSPATIENT: return "Plane Position (Patient) Functional Group Macro"; break;
-    /// Plane Orientation (Patient)
-    case EFG_PLANEORIENTPATIENT: return "Plane Orientation (Patient) Functional Group Macro"; break;
-    /// Derivation Image
-    case EFG_DERIVATIONIMAGE: return "Derivation Image Functional Group Macro"; break;
-    /// Cardiac Synchronization
-    case EFG_CARDIACSYNC: return "Cardiac Synchronization Functional Group Macro"; break;
-    /// Frame Anatomy
-    case EFG_FRAMEANATOMY: return "Frame Anatomy Functional Group Macro"; break;
-    /// Pixel Value Transformation or Identity Pixel Value Transformation
-    case EFG_PIXELVALUETRANSMETA: return "Pixel Value Transformation / Identity Pixel Value Transformation Functional Group Macro"; break;
-    /// Frame VOI LUT or Frame VOI LUT with LUT
-    case EFG_FRAMEVOILUTMETA: return "Frame VOI LUT / Frame VOI LUT with LUT Macro"; break;
-    /// Real World Value Mapping
-    case EFG_REALWORLDVALUEMAPPING: return "Real World Value Mapping Functional Group Macro"; break;
-    /// Contrast/Bolus Usage
-    case EFG_CONTRASTBOLUSUSAGE: return "Contrast/Bolus Usage Group Macro"; break;
-    /// Pixel Intensity Relationship LUT
-    case EFG_PIXELINTENSITYRELLUT: return "Pixel Intensity Relation LUT Functional Group Macro"; break;
-    /// Frame Pixel Shift
-    case EFG_FRAMEPIXELSHIFT: return "Frame Pixel Shift Functional Group Macro"; break;
-    /// Patient Orientation in Frame
-    case EFG_PATIENTORIENTINFRAME: return "Patient Orientation in Frame Functional Group Macro"; break;
-    /// Frame Display Shutter
-    case EFG_FRAMEDISPLAYSHUTTER: return "Frame Display Shutter Functional Group Macro"; break;
-    /// Respiratory Synchronization
-    case EFG_RESPIRATORYSYNC: return "Respiratory Synchronization Functional Group Macro"; break;
-    /// Irradiation Event Identification
-    case EFG_IRRADIATIONEVENTIDENT: return "Irradiation Event Identification Functional Group Macro"; break;
-    /// Radiopharmaceutical Usage
-    case EFG_RADIOPHARAMAUSAGE: return "Radiopharmaceutical Usage Functional Group Macro"; break;
-    /// Parametric Map Frame Type
-    case EFG_PARAMETRICMAPFRAMETYPE: return "Parametric Map Frame Type Functional Group Macro"; break;
-    /// Patient Physiological State
-    case EFG_PATIENTPHYSIOSTATE: return "Patient Physiological State Functional Group Macro"; break;
-    /// Plane Position (Volume)
-    case EFG_PLANEPOSITIONVOLUME: return "Plane Position (Volume) Functional Group Macro"; break;
-    /// Plane Orientation (Volume)
-    case EFG_PLANEORIENTVOLUME: return "Plane Orientation (Volume) Functional Group Macro"; break;
-    /// Temporal Position Macro
-    case EFG_TEMPORALPOSITION: return "Temporal Position Functional Group Macro"; break;
-    /// Image Data Type
-    case EFG_IMAGEDATATYPE: return "Image Data Type Functional Group Macro"; break;
-    /// Unassigned Shared Converted Attributes Macro
-    case EFG_UNASSIGNEDSHAREDCONVERTEDATTRIBUTES: return "Unassigned Shared Converted Attributes Macro"; break;
-    /// Segmentation Macro
-    case EFG_SEGMENTATION: return "Segmentation Functional Group Macro"; break;
-    /// US Image Description Functional Group Macro
-    case EFG_USIMAGEDESCRIPTION: return "US Image Description Functional Group Macro"; break;
-  }
-  return "Unknown Functional Group Macro (internal error)";
+    switch (fgType)
+    {
+        /// Undefined functional group
+        case EFG_UNDEFINED:
+            return "Undefined Functional Group Macro";
+            break;
+        /// Unknown functional group
+        case EFG_UNKNOWN:
+            return "Unknown Functional Group Macro";
+            break;
+        /// Pixel Measures
+        case EFG_PIXELMEASURES:
+            return "Pixel Measures Functional Group Macro";
+            break;
+        /// Frame Content
+        case EFG_FRAMECONTENT:
+            return "Frame Content Functional Group Macro";
+            break;
+        /// CT Acquisition Details
+        case EFG_CTACQUISITIONDETAILS:
+            return "CT Acquisition Details Functional Group Macro";
+            break;
+        /// CT Acquisition Type
+        case EFG_CTACQUISITIONTYPE:
+            return "CT Acquisition Type Functional Group Macro";
+            break;
+        /// CT Additional X-Ray Source
+        case EFG_CTADDITIONALXRAYSOURCE:
+            return "CT Additional X-Ray Source";
+            break;
+        /// CT Exposure
+        case EFG_CTEXPOSURE:
+            return "CT Exposure Functional Group Macro";
+            break;
+        case EFG_CTGEOMETRY:
+            return "CT Geometry Functional Group Macro";
+        /// CT Image Frame Type
+        case EFG_CTIMAGEFRAMETYPE:
+            return "CT Image Frame Type Functional Group Macro";
+            break;
+        /// CT Position
+        case EFG_CTPOSITION:
+            return "CT Position Functional Group Macro";
+            break;
+        /// CT Reconstruction
+        case EFG_CTRECONSTRUCTION:
+            return "CT Reconstruction Functional Group Macro";
+            break;
+        /// CT Table Dynamics
+        case EFG_CTTABLEDYNAMICS:
+            return "CT Table Dynamics Functional Group Macro";
+            break;
+        /// CT X-Ray Details
+        case EFG_CTXRAYDETAILS:
+            return "CT X-Ray Details Functional Group Macro";
+            break;
+        /// Plane Position (Patient)
+        case EFG_PLANEPOSPATIENT:
+            return "Plane Position (Patient) Functional Group Macro";
+            break;
+        /// Plane Orientation (Patient)
+        case EFG_PLANEORIENTPATIENT:
+            return "Plane Orientation (Patient) Functional Group Macro";
+            break;
+        /// Derivation Image
+        case EFG_DERIVATIONIMAGE:
+            return "Derivation Image Functional Group Macro";
+            break;
+        /// Cardiac Synchronization
+        case EFG_CARDIACSYNC:
+            return "Cardiac Synchronization Functional Group Macro";
+            break;
+        /// Frame Anatomy
+        case EFG_FRAMEANATOMY:
+            return "Frame Anatomy Functional Group Macro";
+            break;
+        /// Pixel Value Transformation or Identity Pixel Value Transformation
+        case EFG_PIXELVALUETRANSMETA:
+            return "[CT|Identity] Pixel Value Transformation Functional Group Macro";
+            break;
+        /// Frame VOI LUT or Frame VOI LUT with LUT
+        case EFG_FRAMEVOILUTMETA:
+            return "Frame VOI LUT / Frame VOI LUT with LUT Macro";
+            break;
+        /// Real World Value Mapping
+        case EFG_REALWORLDVALUEMAPPING:
+            return "Real World Value Mapping Functional Group Macro";
+            break;
+        /// Contrast/Bolus Usage
+        case EFG_CONTRASTBOLUSUSAGE:
+            return "Contrast/Bolus Usage Group Macro";
+            break;
+        /// Pixel Intensity Relationship LUT
+        case EFG_PIXELINTENSITYRELLUT:
+            return "Pixel Intensity Relation LUT Functional Group Macro";
+            break;
+        /// Frame Pixel Shift
+        case EFG_FRAMEPIXELSHIFT:
+            return "Frame Pixel Shift Functional Group Macro";
+            break;
+        /// Patient Orientation in Frame
+        case EFG_PATIENTORIENTINFRAME:
+            return "Patient Orientation in Frame Functional Group Macro";
+            break;
+        /// Frame Display Shutter
+        case EFG_FRAMEDISPLAYSHUTTER:
+            return "Frame Display Shutter Functional Group Macro";
+            break;
+        /// Respiratory Synchronization
+        case EFG_RESPIRATORYSYNC:
+            return "Respiratory Synchronization Functional Group Macro";
+            break;
+        /// Irradiation Event Identification
+        case EFG_IRRADIATIONEVENTIDENT:
+            return "Irradiation Event Identification Functional Group Macro";
+            break;
+        /// Radiopharmaceutical Usage
+        case EFG_RADIOPHARAMAUSAGE:
+            return "Radiopharmaceutical Usage Functional Group Macro";
+            break;
+        /// Parametric Map Frame Type
+        case EFG_PARAMETRICMAPFRAMETYPE:
+            return "Parametric Map Frame Type Functional Group Macro";
+            break;
+        /// Patient Physiological State
+        case EFG_PATIENTPHYSIOSTATE:
+            return "Patient Physiological State Functional Group Macro";
+            break;
+        /// Plane Position (Volume)
+        case EFG_PLANEPOSITIONVOLUME:
+            return "Plane Position (Volume) Functional Group Macro";
+            break;
+        /// Plane Orientation (Volume)
+        case EFG_PLANEORIENTVOLUME:
+            return "Plane Orientation (Volume) Functional Group Macro";
+            break;
+        /// Temporal Position Macro
+        case EFG_TEMPORALPOSITION:
+            return "Temporal Position Functional Group Macro";
+            break;
+        /// Image Data Type
+        case EFG_IMAGEDATATYPE:
+            return "Image Data Type Functional Group Macro";
+            break;
+        /// Unassigned Shared Converted Attributes Macro
+        case EFG_UNASSIGNEDSHAREDCONVERTEDATTRIBUTES:
+            return "Unassigned Shared Converted Attributes Macro";
+            break;
+        /// Segmentation Macro
+        case EFG_SEGMENTATION:
+            return "Segmentation Functional Group Macro";
+            break;
+        /// US Image Description Functional Group Macro
+        case EFG_USIMAGEDESCRIPTION:
+            return "US Image Description Functional Group Macro";
+            break;
+    }
+    return "Unknown Functional Group Macro (internal error)";
 }
 
-
 DcmFGTypes::E_FGType DcmFGTypes::tagKey2FGType(const DcmTagKey& key)
 {
-  // Note: Use neat value to enum trick from Alexandrescu in order to have switch statement instead?
-  if (key == DCM_PixelMeasuresSequence)
-    return EFG_PIXELMEASURES;
-  else if (key == DCM_FrameContentSequence)
-    return EFG_FRAMECONTENT;
-  else if (key == DCM_PlanePositionSequence)
-    return EFG_PLANEPOSPATIENT;
-  else if (key == DCM_PlaneOrientationSequence)
-    return EFG_PLANEORIENTPATIENT;
-  else if (key == DCM_DerivationImageSequence)
-    return EFG_DERIVATIONIMAGE;
-  else if (key == DCM_CardiacSynchronizationSequence)
-    return EFG_CARDIACSYNC;
-  else if (key == DCM_FrameAnatomySequence)
-    return EFG_FRAMEANATOMY;
-  else if (key == DCM_PixelValueTransformationSequence)
-    return EFG_PIXELVALUETRANSMETA;
-  else if (key == DCM_FrameVOILUTSequence)
-    return EFG_FRAMEVOILUTMETA;
-  else if (key == DCM_RealWorldValueMappingSequence)
-    return EFG_REALWORLDVALUEMAPPING;
-  else if (key == DCM_ContrastBolusUsageSequence)
-    return EFG_CONTRASTBOLUSUSAGE;
-  else if (key == DCM_PixelIntensityRelationshipLUTSequence)
-    return EFG_PIXELINTENSITYRELLUT;
-  else if (key == DCM_FramePixelShiftSequence)
-    return EFG_FRAMEPIXELSHIFT;
-  else if (key == DCM_PatientOrientationInFrameSequence)
-    return EFG_PATIENTORIENTINFRAME;
-  else if (key == DCM_FrameDisplayShutterSequence)
-    return EFG_FRAMEDISPLAYSHUTTER;
-  else if (key == DCM_RespiratorySynchronizationSequence)
-    return EFG_RESPIRATORYSYNC;
-  else if (key == DCM_IrradiationEventIdentificationSequence)
-    return EFG_IRRADIATIONEVENTIDENT;
-  else if (key == DCM_RadiopharmaceuticalUsageSequence)
-    return EFG_RADIOPHARAMAUSAGE;
-  else if (key == DCM_PatientPhysiologicalStateSequence)
-    return EFG_PATIENTPHYSIOSTATE;
-  else if (key == DCM_ParametricMapFrameTypeSequence)
-    return EFG_PARAMETRICMAPFRAMETYPE;
-  else if (key == DCM_PlanePositionVolumeSequence)
-    return EFG_PLANEPOSITIONVOLUME;
-  else if (key == DCM_PlaneOrientationVolumeSequence)
-    return EFG_PLANEORIENTVOLUME;
-  else if (key == DCM_TemporalPositionSequence)
-    return EFG_TEMPORALPOSITION;
-  else if (key == DCM_ImageDataTypeSequence)
-    return EFG_IMAGEDATATYPE;
-  else if (key == DCM_UnassignedSharedConvertedAttributesSequence)
-    return EFG_UNASSIGNEDSHAREDCONVERTEDATTRIBUTES;
-  else if (key == DCM_SegmentIdentificationSequence)
-    return EFG_SEGMENTATION;
-  else if (key == DCM_USImageDescriptionSequence)
-    return EFG_USIMAGEDESCRIPTION;
-  else
-    return EFG_UNKNOWN;
+    // Note: Use neat value to enum trick from Alexandrescu in order to have switch statement instead?
+    if (key == DCM_PixelMeasuresSequence)
+        return EFG_PIXELMEASURES;
+    else if (key == DCM_FrameContentSequence)
+        return EFG_FRAMECONTENT;
+    else if (key == DCM_CTAcquisitionDetailsSequence)
+        return EFG_CTACQUISITIONDETAILS;
+    else if (key == DCM_CTAdditionalXRaySourceSequence)
+        return EFG_CTADDITIONALXRAYSOURCE;
+    else if (key == DCM_CTAcquisitionTypeSequence)
+        return EFG_CTACQUISITIONTYPE;
+    else if (key == DCM_CTExposureSequence)
+        return EFG_CTEXPOSURE;
+    else if (key == DCM_CTGeometrySequence)
+        return EFG_CTGEOMETRY;
+    else if (key == DCM_CTImageFrameTypeSequence)
+        return EFG_CTIMAGEFRAMETYPE;
+    else if (key == DCM_CTPositionSequence)
+        return EFG_CTPOSITION;
+    else if (key == DCM_CTReconstructionSequence)
+        return EFG_CTRECONSTRUCTION;
+    else if (key == DCM_CTTableDynamicsSequence)
+        return EFG_CTTABLEDYNAMICS;
+    else if (key == DCM_CTXRayDetailsSequence)
+        return EFG_CTXRAYDETAILS;
+    else if (key == DCM_PlanePositionSequence)
+        return EFG_PLANEPOSPATIENT;
+    else if (key == DCM_PlaneOrientationSequence)
+        return EFG_PLANEORIENTPATIENT;
+    else if (key == DCM_DerivationImageSequence)
+        return EFG_DERIVATIONIMAGE;
+    else if (key == DCM_CardiacSynchronizationSequence)
+        return EFG_CARDIACSYNC;
+    else if (key == DCM_FrameAnatomySequence)
+        return EFG_FRAMEANATOMY;
+    else if (key == DCM_PixelValueTransformationSequence)
+        return EFG_PIXELVALUETRANSMETA;
+    else if (key == DCM_FrameVOILUTSequence)
+        return EFG_FRAMEVOILUTMETA;
+    else if (key == DCM_RealWorldValueMappingSequence)
+        return EFG_REALWORLDVALUEMAPPING;
+    else if (key == DCM_ContrastBolusUsageSequence)
+        return EFG_CONTRASTBOLUSUSAGE;
+    else if (key == DCM_PixelIntensityRelationshipLUTSequence)
+        return EFG_PIXELINTENSITYRELLUT;
+    else if (key == DCM_FramePixelShiftSequence)
+        return EFG_FRAMEPIXELSHIFT;
+    else if (key == DCM_PatientOrientationInFrameSequence)
+        return EFG_PATIENTORIENTINFRAME;
+    else if (key == DCM_FrameDisplayShutterSequence)
+        return EFG_FRAMEDISPLAYSHUTTER;
+    else if (key == DCM_RespiratorySynchronizationSequence)
+        return EFG_RESPIRATORYSYNC;
+    else if (key == DCM_IrradiationEventIdentificationSequence)
+        return EFG_IRRADIATIONEVENTIDENT;
+    else if (key == DCM_RadiopharmaceuticalUsageSequence)
+        return EFG_RADIOPHARAMAUSAGE;
+    else if (key == DCM_PatientPhysiologicalStateSequence)
+        return EFG_PATIENTPHYSIOSTATE;
+    else if (key == DCM_ParametricMapFrameTypeSequence)
+        return EFG_PARAMETRICMAPFRAMETYPE;
+    else if (key == DCM_PlanePositionVolumeSequence)
+        return EFG_PLANEPOSITIONVOLUME;
+    else if (key == DCM_PlaneOrientationVolumeSequence)
+        return EFG_PLANEORIENTVOLUME;
+    else if (key == DCM_TemporalPositionSequence)
+        return EFG_TEMPORALPOSITION;
+    else if (key == DCM_ImageDataTypeSequence)
+        return EFG_IMAGEDATATYPE;
+    else if (key == DCM_UnassignedSharedConvertedAttributesSequence)
+        return EFG_UNASSIGNEDSHAREDCONVERTEDATTRIBUTES;
+    else if (key == DCM_SegmentIdentificationSequence)
+        return EFG_SEGMENTATION;
+    else if (key == DCM_USImageDescriptionSequence)
+        return EFG_USIMAGEDESCRIPTION;
+    else
+        return EFG_UNKNOWN;
 }
 
-
 OFString DcmFGTypes::tagKey2FGString(const DcmTagKey& key)
 {
-  E_FGType fgtype = tagKey2FGType(key);
-  return FGType2OFString(fgtype);
+    E_FGType fgtype = tagKey2FGType(key);
+    return FGType2OFString(fgtype);
 }
-
-
index 53a3339cc88385855b0a52492eead3dcdc5a24dc..b9d4093120b21734211d909d4085a81f4d43e75f 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  */
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcdeftag.h"
-#include "dcmtk/dcmiod/iodutil.h"
-#include "dcmtk/dcmiod/iodtypes.h"
 #include "dcmtk/dcmfg/fgusimagedescription.h"
+#include "dcmtk/dcmiod/iodtypes.h"
+#include "dcmtk/dcmiod/iodutil.h"
 
 // Constructor
-FGUSImageDescription::FGUSImageDescription() :
-  FGBase(DcmFGTypes::EFG_USIMAGEDESCRIPTION),
-  m_FrameType(DCM_FrameType),
-  m_VolumetricProperties(DCM_VolumetricProperties),
-  m_VolumeBasedCalculationTechnique(DCM_VolumeBasedCalculationTechnique)
+FGUSImageDescription::FGUSImageDescription()
+    : FGBase(DcmFGTypes::EFG_USIMAGEDESCRIPTION)
+    , m_FrameType(DCM_FrameType)
+    , m_VolumetricProperties(DCM_VolumetricProperties)
+    , m_VolumeBasedCalculationTechnique(DCM_VolumeBasedCalculationTechnique)
 {
 }
 
-
 FGUSImageDescription::~FGUSImageDescription()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
 FGBase* FGUSImageDescription::clone() const
 {
-  FGUSImageDescription* copy = new FGUSImageDescription();
-  if (copy)
-  {
-    copy->m_FrameType = this->m_FrameType;
-    copy->m_VolumetricProperties = this->m_VolumetricProperties;
-    copy->m_VolumeBasedCalculationTechnique = this->m_VolumeBasedCalculationTechnique;
-  }
-  return copy;
+    FGUSImageDescription* copy = new FGUSImageDescription();
+    if (copy)
+    {
+        copy->m_FrameType                       = this->m_FrameType;
+        copy->m_VolumetricProperties            = this->m_VolumetricProperties;
+        copy->m_VolumeBasedCalculationTechnique = this->m_VolumeBasedCalculationTechnique;
+    }
+    return copy;
 }
 
-
 void FGUSImageDescription::clearData()
 {
-  m_FrameType.clear();
-  m_VolumetricProperties.clear();
-  m_VolumeBasedCalculationTechnique.clear();
+    m_FrameType.clear();
+    m_VolumetricProperties.clear();
+    m_VolumeBasedCalculationTechnique.clear();
 }
 
-
 OFCondition FGUSImageDescription::check() const
 {
-  // Checks in read() and write() are sufficient for now
-  return EC_Normal;
+    // Checks in read() and write() are sufficient for now
+    return EC_Normal;
 }
 
-
 // --- get() functionality ---
 
-OFCondition FGUSImageDescription::getFrameType(OFString& value,
-                                               const long signed int pos)
+OFCondition FGUSImageDescription::getFrameType(OFString& value, const long signed int pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_FrameType, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_FrameType, value, pos);
 }
 
-
-OFCondition FGUSImageDescription::getVolumetricProperties(OFString& value,
-                                                          const long signed int pos)
+OFCondition FGUSImageDescription::getVolumetricProperties(OFString& value, const long signed int pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_VolumetricProperties, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_VolumetricProperties, value, pos);
 }
 
-
-OFCondition FGUSImageDescription::getVolumeBasedCalculationTechnique(OFString& value,
-                                                                     const long signed int pos)
+OFCondition FGUSImageDescription::getVolumeBasedCalculationTechnique(OFString& value, const long signed int pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_VolumeBasedCalculationTechnique, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_VolumeBasedCalculationTechnique, value, pos);
 }
 
-
 // --- set() functionality ---
 
-
 OFCondition FGUSImageDescription::setFrameType(const DcmFGTypes::E_FGUSFrameType pixelDataChar,
                                                const OFString& imageFlavor,
                                                const OFString& derivedPixelContrast,
                                                const OFBool checkValue)
 {
-  // Build a string of VM 4 with first two values at least set
-  OFString value;
-  switch (pixelDataChar)
-  {
-    case(DcmFGTypes::EFGFT_ORIGINAL): value = "ORIGINAL\\PRIMARY\\"; break;
-    case(DcmFGTypes::EFGFT_DERIVED) : value = "DERIVED\\PRIMARY\\"; break;
-    default: return IOD_EC_InvalidElementValue;
-  }
-  value += imageFlavor;
-  value += "\\";
-  value += derivedPixelContrast;
-
-  OFCondition result;
-  if (checkValue)
-  {
-    result = DcmCodeString::checkStringValue(value, "4");
-  }
-  if (result.good())
-  {
-    result = m_FrameType.putOFStringArray(value);
-  }
-  return result;
+    // Build a string of VM 4 with first two values at least set
+    OFString value;
+    switch (pixelDataChar)
+    {
+        case (DcmFGTypes::EFGFT_ORIGINAL):
+            value = "ORIGINAL\\PRIMARY\\";
+            break;
+        case (DcmFGTypes::EFGFT_DERIVED):
+            value = "DERIVED\\PRIMARY\\";
+            break;
+        default:
+            return IOD_EC_InvalidElementValue;
+    }
+    value += imageFlavor;
+    value += "\\";
+    value += derivedPixelContrast;
+
+    OFCondition result;
+    if (checkValue)
+    {
+        result = DcmCodeString::checkStringValue(value, "4");
+    }
+    if (result.good())
+    {
+        result = m_FrameType.putOFStringArray(value);
+    }
+    return result;
 }
 
-
-OFCondition FGUSImageDescription::setVolumetricProperties(const OFString& value,
-                                                          const OFBool checkValue)
+OFCondition FGUSImageDescription::setVolumetricProperties(const OFString& value, const OFBool checkValue)
 {
- OFCondition result;
- if (checkValue)
- {
-   if ( (value != "VOLUME") && (value != "SAMPLED") && (value != "DISTORTED") && (value != "MIXED") )
-   {
-     result = IOD_EC_InvalidElementValue;
-   }
-   else
-     result = DcmCodeString::checkStringValue(value, "1");
- }
- if (result.good())
- {
-   result = m_VolumetricProperties.putOFStringArray(value);
- }
-  return result;
   OFCondition result;
   if (checkValue)
   {
+        if ((value != "VOLUME") && (value != "SAMPLED") && (value != "DISTORTED") && (value != "MIXED"))
+        {
+            result = IOD_EC_InvalidElementValue;
+        }
+        else
+            result = DcmCodeString::checkStringValue(value, "1");
   }
   if (result.good())
   {
+        result = m_VolumetricProperties.putOFStringArray(value);
   }
+    return result;
 }
 
-
-OFCondition FGUSImageDescription::setVolumeBasedCalculationTechnique(const OFString& value,
-                                                                     const OFBool checkValue)
+OFCondition FGUSImageDescription::setVolumeBasedCalculationTechnique(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_VolumeBasedCalculationTechnique.putOFStringArray(value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_VolumeBasedCalculationTechnique.putOFStringArray(value);
+    return result;
 }
 
-
 /// Read Frame Content Sequence from given item
 OFCondition FGUSImageDescription::read(DcmItem& item)
 {
-  clearData();
+    clearData();
 
-  DcmItem* seqItem = NULL;
-  OFCondition result = getItemFromFGSequence(item, DCM_USImageDescriptionSequence, 0, seqItem);
-  if (result.bad())
-    return result;
+    DcmItem* seqItem   = NULL;
+    OFCondition result = getItemFromFGSequence(item, DCM_USImageDescriptionSequence, 0, seqItem);
+    if (result.bad())
+        return result;
 
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FrameType, "4", "1", "USImageDescriptionMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_VolumetricProperties, "1", "1", "USImageDescriptionMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_VolumeBasedCalculationTechnique, "1", "1", "USImageDescriptionMacro");
-  return result;
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_FrameType, "4", "1", "USImageDescriptionMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(*seqItem, m_VolumetricProperties, "1", "1", "USImageDescriptionMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(
+        *seqItem, m_VolumeBasedCalculationTechnique, "1", "1", "USImageDescriptionMacro");
+    return result;
 }
 
-
 /// Writes single Frame Content Sequence into given item
 OFCondition FGUSImageDescription::write(DcmItem& item)
 {
-  DcmItem *seqItem = NULL;
-  OFCondition result = createNewFGSequence(item, DCM_USImageDescriptionSequence, 0, seqItem);
-  if (result.bad())
-    return result;
+    DcmItem* seqItem   = NULL;
+    OFCondition result = createNewFGSequence(item, DCM_USImageDescriptionSequence, 0, seqItem);
+    if (result.bad())
+        return result;
 
-  // --- write frame content macro attributes ---
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_FrameType, "4", "1", "USImageDescriptionMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_VolumetricProperties, "1", "1", "USImageDescriptionMacro");
-  DcmIODUtil::copyElementToDataset(result, *seqItem, m_VolumeBasedCalculationTechnique, "1", "1", "USImageDescriptionMacro");
+    // --- write frame content macro attributes ---
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_FrameType, "4", "1", "USImageDescriptionMacro");
+    DcmIODUtil::copyElementToDataset(result, *seqItem, m_VolumetricProperties, "1", "1", "USImageDescriptionMacro");
+    DcmIODUtil::copyElementToDataset(
+        result, *seqItem, m_VolumeBasedCalculationTechnique, "1", "1", "USImageDescriptionMacro");
 
-  return result;
+    return result;
 }
 
-
 int FGUSImageDescription::compare(const FGBase& rhs) const
 {
-  int result = FGBase::compare(rhs);
-  if (result != 0)
-    return result;
+    int result = FGBase::compare(rhs);
+    if (result != 0)
+        return result;
 
-  const FGUSImageDescription* myRhs = OFstatic_cast(const FGUSImageDescription*, &rhs);
-  if (!myRhs)
-    return -1;
+    const FGUSImageDescription* myRhs = OFstatic_cast(const FGUSImageDescription*, &rhs);
+    if (!myRhs)
+        return -1;
 
-  // Compare all elements
-  result = m_FrameType.compare(myRhs->m_FrameType);
-  if (result == 0)
-    result = m_VolumetricProperties.compare(myRhs->m_VolumetricProperties);
-  if (result == 0)
-    result = m_VolumeBasedCalculationTechnique.compare(myRhs->m_VolumeBasedCalculationTechnique);
+    // Compare all elements
+    result = m_FrameType.compare(myRhs->m_FrameType);
+    if (result == 0)
+        result = m_VolumetricProperties.compare(myRhs->m_VolumetricProperties);
+    if (result == 0)
+        result = m_VolumeBasedCalculationTechnique.compare(myRhs->m_VolumeBasedCalculationTechnique);
 
-  return result;
+    return result;
 }
index d59f1f4d9d72c1c2097bbcf2dd27356b54c3f039..1a3913a0e2e952d4b9540379ee03c4f43973b50e 100644 (file)
  */
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmfg/stack.h"
 
+#include "dcmtk/dcmfg/stack.h"
 
-FGStack::FGStack(const OFString& stackID,
-                 const OFMap< Uint32, Uint32 > frameNumbers)
-: m_StackID(stackID),
-  m_FrameNumbers(frameNumbers)
+FGStack::FGStack(const OFString& stackID, const OFMap<Uint32, Uint32> frameNumbers)
+    : m_StackID(stackID)
+    , m_FrameNumbers(frameNumbers)
 {
-
 }
 
 FGStack::FGStack(const OFString& stackID)
-: m_StackID(stackID),
-  m_FrameNumbers()
+    : m_StackID(stackID)
+    , m_FrameNumbers()
 {
-
 }
 
-OFBool FGStack::addFrame(const Uint32 frameNumber,
-                         const Uint32 inStackPos)
+OFBool FGStack::addFrame(const Uint32 frameNumber, const Uint32 inStackPos)
 {
-  m_FrameNumbers.insert(OFMake_pair(frameNumber, inStackPos));
-  return OFTrue;
+    m_FrameNumbers.insert(OFMake_pair(frameNumber, inStackPos));
+    return OFTrue;
 }
 
-
 FGStack::~FGStack()
 {
-
 }
 
-
 FGStack::const_iterator FGStack::begin() const
 {
-  return m_FrameNumbers.begin();
+    return m_FrameNumbers.begin();
 }
 
-
 FGStack::iterator FGStack::begin()
 {
-  return m_FrameNumbers.begin();
+    return m_FrameNumbers.begin();
 }
 
-
 FGStack::const_iterator FGStack::end() const
 {
-  return m_FrameNumbers.end();
+    return m_FrameNumbers.end();
 }
 
-
 FGStack::iterator FGStack::end()
 {
-  return m_FrameNumbers.end();
+    return m_FrameNumbers.end();
 }
 
-
 OFString FGStack::getStackID() const
 {
-  return m_StackID;
+    return m_StackID;
 }
 
-
 Uint32 FGStack::getInStackPos(const Uint32 frameNumber) const
 {
-  FGStack::const_iterator it = m_FrameNumbers.find(frameNumber);
-  if (it == m_FrameNumbers.end())
-     return 0;
-  else
-    return (*it).second;
+    FGStack::const_iterator it = m_FrameNumbers.find(frameNumber);
+    if (it == m_FrameNumbers.end())
+        return 0;
+    else
+        return (*it).second;
 }
 
-
-void FGStack::getFramesAtStackPos(const Uint32 inStackPos,
-                                  OFVector<Uint32>& resultFrameNumbers)
+void FGStack::getFramesAtStackPos(const Uint32 inStackPos, OFVector<Uint32>& resultFrameNumbers)
 {
-  FGStack::iterator it = m_FrameNumbers.begin();
-  while (it != m_FrameNumbers.end())
-  {
-    if ((*it).second == inStackPos)
+    FGStack::iterator it = m_FrameNumbers.begin();
+    while (it != m_FrameNumbers.end())
     {
-      resultFrameNumbers.push_back( (*it).second);
+        if ((*it).second == inStackPos)
+        {
+            resultFrameNumbers.push_back((*it).second);
+        }
+        it++;
     }
-    it++;
-  }
 }
index c9e0c32a073804cbf45f688ab68ee2d16b4cc291..54a28575a58f0f754f54fa90cbf2f729e436be28 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmiod/iodutil.h"
 #include "dcmtk/dcmfg/stackinterface.h"
+#include "dcmtk/config/osconfig.h"
 #include "dcmtk/dcmfg/fgfracon.h"
-
+#include "dcmtk/dcmiod/iodutil.h"
 
 FGStackInterface::FGStackInterface()
-: m_Stacks()
+    : m_Stacks()
 {
 }
 
-
 FGStackInterface::~FGStackInterface()
 {
-  while (m_Stacks.size() != 0)
-  {
-    OFMap<OFString,FGStack*>::iterator it = m_Stacks.begin();
-    FGStack *toDelete = (*it).second;
-    m_Stacks.erase(it);
-    delete toDelete;
-  }
+    while (m_Stacks.size() != 0)
+    {
+        OFMap<OFString, FGStack*>::iterator it = m_Stacks.begin();
+        FGStack* toDelete                      = (*it).second;
+        m_Stacks.erase(it);
+        delete toDelete;
+    }
 }
 
-
 void FGStackInterface::clear()
 {
-  size_t stackSize = m_Stacks.size();
-  OFMap<OFString, FGStack*>::iterator it;
-  for (size_t count = 0; count < stackSize; count++)
-  {
-    it = m_Stacks.begin();
-    m_Stacks.erase(it);
-  }
+    size_t stackSize = m_Stacks.size();
+    OFMap<OFString, FGStack*>::iterator it;
+    for (size_t count = 0; count < stackSize; count++)
+    {
+        it = m_Stacks.begin();
+        m_Stacks.erase(it);
+    }
 }
 
-
 OFCondition FGStackInterface::read(FGInterface& fgSource)
 {
-  clear();
-  size_t numFrames = fgSource.getNumberOfFrames();
-  for (size_t count = 0; count < numFrames; count++)
-  {
-    // Get frame content FG if existing
-    FGFrameContent* fracon = OFstatic_cast(FGFrameContent*, fgSource.get(OFstatic_cast(Uint32, count), DcmFGTypes::EFG_FRAMECONTENT));
-    if (fracon != NULL)
+    clear();
+    size_t numFrames = fgSource.getNumberOfFrames();
+    for (size_t count = 0; count < numFrames; count++)
     {
-      OFString stackID;
-      Uint32 inStackPos;
-      // Check whether stack ID is actually present and get value
-      if ( (fracon->getStackID(stackID).good()) && (fracon->getInStackPositionNumber(inStackPos).good()) )
-      {
-        // Check whether this is a stack ID we do not know yet
-        OFMap<OFString, FGStack*>::iterator it = m_Stacks.begin();
-        while (it != m_Stacks.end())
+        // Get frame content FG if existing
+        FGFrameContent* fracon
+            = OFstatic_cast(FGFrameContent*, fgSource.get(OFstatic_cast(Uint32, count), DcmFGTypes::EFG_FRAMECONTENT));
+        if (fracon != NULL)
         {
-          // If this is an old stack, add frame to it
-          if ( (*it).second->getStackID() == stackID)
-          {
-            // Add frame to stack if it is not in yet
-            if ( (*it).second->getInStackPos(OFstatic_cast(Uint32, count)) == 0)
+            OFString stackID;
+            Uint32 inStackPos;
+            // Check whether stack ID is actually present and get value
+            if ((fracon->getStackID(stackID).good()) && (fracon->getInStackPositionNumber(inStackPos).good()))
             {
-              (*it).second->addFrame(OFstatic_cast(Uint32, count), inStackPos);
+                // Check whether this is a stack ID we do not know yet
+                OFMap<OFString, FGStack*>::iterator it = m_Stacks.begin();
+                while (it != m_Stacks.end())
+                {
+                    // If this is an old stack, add frame to it
+                    if ((*it).second->getStackID() == stackID)
+                    {
+                        // Add frame to stack if it is not in yet
+                        if ((*it).second->getInStackPos(OFstatic_cast(Uint32, count)) == 0)
+                        {
+                            (*it).second->addFrame(OFstatic_cast(Uint32, count), inStackPos);
+                        }
+                    }
+                    it++;
+                }
+                // If this is a new stack, add it to the list
+                if (it == m_Stacks.end())
+                {
+                    FGStack* stack = new FGStack(stackID);
+                    if (stack == NULL)
+                    {
+                        return EC_MemoryExhausted;
+                    }
+                    stack->addFrame(OFstatic_cast(Uint32, count), inStackPos);
+                    if (!m_Stacks.insert(OFMake_pair(stack->getStackID(), stack)).second)
+                    {
+                        delete stack;
+                        DCMFG_ERROR("Could not add stack to internal list (internal error, ignored)");
+                    }
+                }
+            }
+            else
+            {
+                DCMFG_WARN("Reading stacks but Frame " << count << " does not provide Stack ID or In-Stack Position");
             }
-          }
-          it++;
         }
-        // If this is a new stack, add it to the list
-        if (it == m_Stacks.end())
+        else
         {
-          FGStack *stack = new FGStack(stackID);
-          if (stack == NULL)
-          {
-            return EC_MemoryExhausted;
-          }
-          stack->addFrame(OFstatic_cast(Uint32, count), inStackPos);
-          if ( !m_Stacks.insert(OFMake_pair(stack->getStackID(), stack)).second )
-          {
-            delete stack;
-            DCMFG_ERROR("Could not add stack to internal list (internal error, ignored)");
-          }
+            DCMFG_WARN("Reading stacks but Frame " << count << " does not provide a Frame Content functional group");
         }
-      }
-      else
-      {
-        DCMFG_WARN("Reading stacks but Frame " << count << " does not provide Stack ID or In-Stack Position");
-      }
     }
-    else
+
+    if (m_Stacks.size() == 0)
     {
-      DCMFG_WARN("Reading stacks but Frame " << count << " does not provide a Frame Content functional group");
+        return FG_EC_NoStacksFound;
     }
-  }
-
-  if (m_Stacks.size() == 0)
-  {
-    return FG_EC_NoStacksFound;
-  }
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 OFCondition FGStackInterface::write(FGInterface& fgDestination)
 {
-  size_t numFrames = fgDestination.getNumberOfFrames();
-  if (numFrames == 0)
-  {
-    return FG_EC_NotEnoughFrames;
-  }
+    size_t numFrames = fgDestination.getNumberOfFrames();
+    if (numFrames == 0)
+    {
+        return FG_EC_NotEnoughFrames;
+    }
 
-  // Check whether maximum in-stack position does not exceed number of frames in image
-  if (!checkConsistency(&fgDestination))
-  {
-    return FG_EC_InvalidData;
-  }
+    // Check whether maximum in-stack position does not exceed number of frames in image
+    if (!checkConsistency(&fgDestination))
+    {
+        return FG_EC_InvalidData;
+    }
 
-  // Walk through stacks, and for each, add/overwrite stack information to
-  // the respective Frame Content functional groups
-  OFCondition result;
-  OFMap<OFString, FGStack*>::iterator stack = m_Stacks.begin();
-  while (result.good() && (stack != m_Stacks.end()) )
-  {
-    OFString stackID =  (*stack).second->getStackID();
-    // Walk over all referenced frames and add Stack information
-    OFMap<Uint32, Uint32>::const_iterator stackEntry = (*stack).second->begin();
-    while (stackEntry != (*stack).second->end())
+    // Walk through stacks, and for each, add/overwrite stack information to
+    // the respective Frame Content functional groups
+    OFCondition result;
+    OFMap<OFString, FGStack*>::iterator stack = m_Stacks.begin();
+    while (result.good() && (stack != m_Stacks.end()))
     {
-      Uint32 frameNo = (*stackEntry).first;
-      Uint32 inStackPos = (*stackEntry).second;
-      FGFrameContent* fg = ensureFrameContentFG(frameNo, fgDestination);
-      // Create functional group if not already existing
-      if (fg == NULL)
-      {
-        result = FG_EC_CouldNotAddFG;
-      }
-      if (result.good()) result = fg->setStackID(stackID);
-      if (result.good()) result = fg->setInStackPositionNumber(inStackPos+1 /* vector counts from 0, position in DICOM starts with 1 */);
-      if (result.bad())
-      {
-        DCMFG_ERROR("Could not create or add stack with ID " << stackID << " to frame " << frameNo << ": " << result.text());
-      }
-      stackEntry++;
+        OFString stackID = (*stack).second->getStackID();
+        // Walk over all referenced frames and add Stack information
+        OFMap<Uint32, Uint32>::const_iterator stackEntry = (*stack).second->begin();
+        while (stackEntry != (*stack).second->end())
+        {
+            Uint32 frameNo     = (*stackEntry).first;
+            Uint32 inStackPos  = (*stackEntry).second;
+            FGFrameContent* fg = ensureFrameContentFG(frameNo, fgDestination);
+            // Create functional group if not already existing
+            if (fg == NULL)
+            {
+                result = FG_EC_CouldNotAddFG;
+            }
+            if (result.good())
+                result = fg->setStackID(stackID);
+            if (result.good())
+                result = fg->setInStackPositionNumber(inStackPos
+                                                      + 1 /* vector counts from 0, position in DICOM starts with 1 */);
+            if (result.bad())
+            {
+                DCMFG_ERROR("Could not create or add stack with ID " << stackID << " to frame " << frameNo << ": "
+                                                                     << result.text());
+            }
+            stackEntry++;
+        }
+        stack++;
     }
-    stack++;
-  }
-  return result;
+    return result;
 }
 
-
-FGFrameContent* FGStackInterface::ensureFrameContentFG(const Uint32 frameNo,
-                                                       FGInterface& fg)
+FGFrameContent* FGStackInterface::ensureFrameContentFG(const Uint32 frameNo, FGInterface& fg)
 {
-  FGFrameContent* content = OFstatic_cast(FGFrameContent*, fg.get(frameNo, DcmFGTypes::EFG_FRAMECONTENT));
-  if (!content)
-  {
-    FGFrameContent newContent;
-    OFCondition result = fg.addPerFrame(frameNo, newContent);
-    if (result.bad())
-    {
-      DCMFG_ERROR("Could not add Frame Content FG for frame " << frameNo);
-    }
-    else
+    FGFrameContent* content = OFstatic_cast(FGFrameContent*, fg.get(frameNo, DcmFGTypes::EFG_FRAMECONTENT));
+    if (!content)
     {
-      content = OFstatic_cast(FGFrameContent*, fg.get(frameNo, DcmFGTypes::EFG_FRAMECONTENT));
+        FGFrameContent newContent;
+        OFCondition result = fg.addPerFrame(frameNo, newContent);
+        if (result.bad())
+        {
+            DCMFG_ERROR("Could not add Frame Content FG for frame " << frameNo);
+        }
+        else
+        {
+            content = OFstatic_cast(FGFrameContent*, fg.get(frameNo, DcmFGTypes::EFG_FRAMECONTENT));
+        }
     }
-  }
-  return content;
+    return content;
 }
 
-
 OFBool FGStackInterface::addStack(FGStack* stack)
 {
-  if (stack == NULL)
-    return OFFalse;
+    if (stack == NULL)
+        return OFFalse;
 
-  if (stack->getStackID().empty())
-  {
-    DCMFG_ERROR("Stack ID cannot be empty");
-    return OFFalse;
-  }
+    if (stack->getStackID().empty())
+    {
+        DCMFG_ERROR("Stack ID cannot be empty");
+        return OFFalse;
+    }
 
-  return m_Stacks.insert(OFMake_pair(stack->getStackID(), stack)).second;
+    return m_Stacks.insert(OFMake_pair(stack->getStackID(), stack)).second;
 }
 
-
 size_t FGStackInterface::numStacks() const
 {
-  return m_Stacks.size();
+    return m_Stacks.size();
 }
 
-
 OFBool FGStackInterface::checkConsistency(FGInterface* fgContext)
 {
-  size_t errors = 0;
-  size_t count = 0;
-  // Run over stacks and check whether each has a Stack ID.
-  // Also check whether stacks can be valid in the context
-  // of the given functional groups (e.g. frame range ok)
-  OFMap<OFString, FGStack*>::iterator it = m_Stacks.begin();
-  while (it != m_Stacks.end())
-  {
-    if ( (*it).second->getStackID().empty())
+    size_t errors = 0;
+    size_t count  = 0;
+    // Run over stacks and check whether each has a Stack ID.
+    // Also check whether stacks can be valid in the context
+    // of the given functional groups (e.g. frame range ok)
+    OFMap<OFString, FGStack*>::iterator it = m_Stacks.begin();
+    while (it != m_Stacks.end())
     {
-      errors++;
-      DCMFG_ERROR("Stack ID for stack #" << count << " is empty");
-    }
-    if (fgContext)
-    {
-      errors += checkContext((*it).second, fgContext);
+        if ((*it).second->getStackID().empty())
+        {
+            errors++;
+            DCMFG_ERROR("Stack ID for stack #" << count << " is empty");
+        }
+        if (fgContext)
+        {
+            errors += checkContext((*it).second, fgContext);
+        }
+        it++;
+        count++;
     }
-    it++;
-    count++;
-  }
-  return (errors == 0);
+    return (errors == 0);
 }
 
-
-size_t FGStackInterface::checkContext(FGStack* stack,
-                                      FGInterface* context)
+size_t FGStackInterface::checkContext(FGStack* stack, FGInterface* context)
 {
-  // Must be non-empty
-  if ( !stack || !context)
-    return 1;
-
-  // Check whether we have any frames
-  size_t numFrames = context->getNumberOfFrames();
-  if (numFrames == 0)
-  {
-    DCMFG_ERROR("Cannot have stacks without frames");
-    return 1;
-  }
+    // Must be non-empty
+    if (!stack || !context)
+        return 1;
 
-  // Walk over frames in stack and check that frame number and
-  // in-stack position is in range with the number of available frames
-  size_t errors = 0;
-  const OFMap<Uint32,Uint32>& frames = stack->m_FrameNumbers;
-  FGStack::const_iterator it = frames.begin();
-  for (size_t count = 0; count < numFrames; count++)
-  {
-    // Frame number must be in range
-    if ( (*it).first > numFrames )
+    // Check whether we have any frames
+    size_t numFrames = context->getNumberOfFrames();
+    if (numFrames == 0)
     {
-      DCMFG_ERROR("Stack references frame #" << (*it).first << " but only #" << numFrames << " frames exist");
-      errors++;
+        DCMFG_ERROR("Cannot have stacks without frames");
+        return 1;
     }
-    if ( (*it).second> numFrames )
+
+    // Walk over frames in stack and check that frame number and
+    // in-stack position is in range with the number of available frames
+    size_t errors                       = 0;
+    const OFMap<Uint32, Uint32>& frames = stack->m_FrameNumbers;
+    FGStack::const_iterator it          = frames.begin();
+    for (size_t count = 0; count < numFrames; count++)
     {
-      DCMFG_ERROR("Stack references in-stack position #" << (*it).first << " but only #" << numFrames << " frames exist");
-      errors++;
+        // Frame number must be in range
+        if ((*it).first > numFrames)
+        {
+            DCMFG_ERROR("Stack references frame #" << (*it).first << " but only #" << numFrames << " frames exist");
+            errors++;
+        }
+        if ((*it).second > numFrames)
+        {
+            DCMFG_ERROR("Stack references in-stack position #" << (*it).first << " but only #" << numFrames
+                                                               << " frames exist");
+            errors++;
+        }
     }
-  }
-  return errors;
+    return errors;
 }
-
index 7407bd0bcc91a00614796efb4042cdf4a5cad21f..9c56a8cf2ec386d259a639cd3d0b40fe7f9ec8b9 100644 (file)
@@ -1,5 +1,16 @@
 # declare executables
-DCMTK_ADD_EXECUTABLE(dcmfg_tests tests t_deriv_image.cc t_frame_content.cc)
+DCMTK_ADD_EXECUTABLE(dcmfg_tests
+                     tests
+                     t_concatenation_creator
+                     t_concatenation_loader
+                     t_ct_acquisition_details
+                     t_ct_acquisition_type
+                     t_ct_image_frame_type
+                     t_ct_position
+                     t_ct_table_dynamics
+                     t_deriv_image
+                     t_frame_content
+                     t_irradiation_event_identification)
 
 # make sure executables are linked to the corresponding libraries
 DCMTK_TARGET_LINK_MODULES(dcmfg_tests dcmfg dcmdata oflog ofstd)
index 8dcc7db6667fcacd1c504d60a345a6349915f5cd..51a0bbec7fb59699be8e8026ad8b41f70b103a09 100644 (file)
@@ -1,24 +1,23 @@
-t_deriv_image.o: t_deriv_image.cc \
+t_concatenation_creator.o: t_concatenation_creator.cc \
  ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmfg/fgderimg.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
- ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
- ../../ofstd/include/dcmtk/ofstd/ofcast.h \
- ../../ofstd/include/dcmtk/ofstd/ofexport.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../include/dcmtk/dcmfg/concatenationcreator.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
@@ -115,39 +114,171 @@ t_deriv_image.o: t_deriv_image.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
- ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
- ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fginterface.h \
- ../include/dcmtk/dcmfg/fg.h ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../../ofstd/include/dcmtk/ofstd/oftempf.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
  ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
  ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
  ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
  ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
  ../../ofstd/include/dcmtk/ofstd/ofexit.h
-t_frame_content.o: t_frame_content.cc \
+t_concatenation_loader.o: t_concatenation_loader.cc \
  ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmfg/fgfracon.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../include/dcmtk/dcmfg/concatenationloader.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftuple.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdiag.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/push.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/mmtag.def \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefrd.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuple.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/pop.def \
+ ../include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstrutl.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h
+t_ct_acquisition_details.o: t_ct_acquisition_details.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmfg/fgctacquisitiondetails.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
@@ -246,11 +377,904 @@ t_frame_content.o: t_frame_content.cc \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
  ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
  ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fginterface.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../include/dcmtk/dcmfg/fg.h ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmfg/fg.h ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h
+t_ct_acquisition_type.o: t_ct_acquisition_type.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmfg/fgctacquisitiontype.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fginterface.h \
+ ../include/dcmtk/dcmfg/fg.h ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h
+t_ct_image_frame_type.o: t_ct_image_frame_type.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmfg/fgctimageframetype.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fginterface.h \
+ ../include/dcmtk/dcmfg/fg.h ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h
+t_ct_position.o: t_ct_position.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmfg/fgctposition.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fginterface.h \
+ ../include/dcmtk/dcmfg/fg.h ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h
+t_ct_table_dynamics.o: t_ct_table_dynamics.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmfg/fgcttabledynamics.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fginterface.h \
+ ../include/dcmtk/dcmfg/fg.h ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h
+t_deriv_image.o: t_deriv_image.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmfg/fgderimg.h ../include/dcmtk/dcmfg/fgbase.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../include/dcmtk/dcmfg/fginterface.h ../include/dcmtk/dcmfg/fg.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h
+t_frame_content.o: t_frame_content.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmfg/fgfracon.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fgbase.h ../include/dcmtk/dcmfg/fgtypes.h \
+ ../include/dcmtk/dcmfg/fgdefine.h ../include/dcmtk/dcmfg/fginterface.h \
+ ../include/dcmtk/dcmfg/fg.h ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h
+t_irradiation_event_identification.o: \
+ t_irradiation_event_identification.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmfg/fginterface.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmfg/fg.h ../include/dcmtk/dcmfg/fgbase.h \
+ ../include/dcmtk/dcmfg/fgtypes.h ../include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../include/dcmtk/dcmfg/fgirradiationeventid.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
  ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
  ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
  ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
index 4f6c07633868e3a3f06c671bc593f6ee142d39f6..4de6261261f9e1dbfcc3a56b0b297abd17dd08eb 100644 (file)
@@ -22,9 +22,21 @@ LIBDIRS = -L$(top_srcdir)/libsrc -L$(ofstddir)/libsrc -L$(oflogdir)/libsrc \
 LOCALLIBS = -ldcmfg -ldcmiod -ldcmdata -loflog -lofstd $(ZLIBLIBS) \
        $(CHARCONVLIBS) $(MATHLIBS)
 LOCALINCLUDES = -I$(top_srcdir)/include -I$(ofstddir)/include -I$(oflogdir)/include \
-       -I$(dcmdatadir)/include -I$(dcmioddir)/include \
+       -I$(dcmdatadir)/include -I$(dcmioddir)/include
+
+test_objs = t_concatenation_creator.o \
+       t_concatenation_loader.o \
+       t_ct_acquisition_details.o \
+       t_ct_acquisition_type.o \
+       t_ct_image_frame_type.o \
+       t_ct_position.o \
+       t_ct_table_dynamics.o \
+       t_deriv_image.o \
+       t_frame_content.o \
+       t_irradiation_event_identification.o \
+       tests.o
+
 
-test_objs = tests.o t_deriv_image.o t_frame_content.o
 objs = $(test_objs)
 progs = tests
 
@@ -36,10 +48,10 @@ tests: $(test_objs)
 
 
 check: tests
-       ./tests
+       DCMDICTPATH=../../dcmdata/data/dicom.dic ./tests
 
 check-exhaustive: tests
-       ./tests -x
+       DCMDICTPATH=../../dcmdata/data/dicom.dic ./tests -x
 
 
 install: all
diff --git a/dcmfg/tests/t_concatenation_creator.cc b/dcmfg/tests/t_concatenation_creator.cc
new file mode 100644 (file)
index 0000000..cdf8e9d
--- /dev/null
@@ -0,0 +1,78 @@
+/*
+ *
+ *  Copyright (C) 2019, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Tests for ConcatenationCreator class
+ *
+ */
+
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+
+#include "dcmtk/dcmfg/concatenationcreator.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/ofstd/ofstd.h"
+#include "dcmtk/ofstd/ofstream.h"
+#include "dcmtk/ofstd/ofstring.h"
+#include "dcmtk/ofstd/oftempf.h"
+#include "dcmtk/ofstd/oftest.h"
+
+// NEMA CT Test files are available at:
+// ftp://medical.nema.org/medical/dicom/Multiframe/CT/nemamfct.images.tar.bz2
+static OFString NEMA_ENHANCED_CT_DIR = "/home/michael/Downloads/NEMA/DISCIMG/IMAGES/";
+static OFString CT1                  = NEMA_ENHANCED_CT_DIR + PATH_SEPARATOR + "CT0001";
+
+OFTEST(dcmfg_concatenation_creator)
+{
+    if (!OFStandard::fileExists(CT1))
+        return;
+    DcmFileFormat dcmff;
+    OFCondition result = dcmff.loadFile(CT1);
+    ConcatenationCreator cc;
+    result = cc.setCfgInput(dcmff.getDataset(), OFFalse /* do not take ownership */);
+    OFCHECK(result.good());
+    if (result.good())
+    {
+        size_t numInstances = cc.getNumInstances();
+        OFCHECK(numInstances == 3);
+        for (size_t i = 0; result.good() && (i < numInstances); i++)
+        {
+            DcmFileFormat destff;
+            result = cc.writeNextInstance(*(destff.getDataset()));
+            OFCHECK(result.good());
+            if (result.good())
+            {
+                OFTempFile tf(O_RDWR, "", "", ".dcm");
+                result = destff.saveFile(tf.getFilename(), EXS_LittleEndianExplicit);
+                OFCHECK(result.good());
+            }
+        }
+    }
+}
+
+OFTEST(dcmfg_concatenation_creator_fail)
+{
+    if (!OFStandard::fileExists(CT1))
+        return;
+    DcmFileFormat dcmff;
+    OFCondition result = dcmff.loadFile(CT1);
+    ConcatenationCreator cc;
+    cc.setCfgFramesPerInstance(55);
+    result = cc.setCfgInput(dcmff.getDataset(), OFFalse /* do not take ownership */);
+    OFCHECK(result.good());
+    OFTempFile tf(O_RDWR, "", "", ".dcm");
+    result = cc.writeNextInstance(tf.getFilename());
+    OFCHECK(result == FG_EC_NotEnoughFrames);
+}
diff --git a/dcmfg/tests/t_concatenation_loader.cc b/dcmfg/tests/t_concatenation_loader.cc
new file mode 100644 (file)
index 0000000..c8d974c
--- /dev/null
@@ -0,0 +1,3149 @@
+/*
+ *
+ *  Copyright (C) 2019-2020, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Tests for Concatenation Creator class
+ *
+ */
+
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+
+#include "dcmtk/dcmfg/concatenationloader.h"
+#include "dcmtk/dcmfg/fgtypes.h"
+#include "dcmtk/dcmiod/iodtypes.h"
+#include "dcmtk/ofstd/ofmap.h"
+#include "dcmtk/ofstd/ofstd.h"
+#include "dcmtk/ofstd/ofstream.h"
+#include "dcmtk/ofstd/ofstring.h"
+#include "dcmtk/ofstd/ofstrutl.h"
+#include "dcmtk/ofstd/oftest.h"
+
+// Path to NEMA example data with trailing slash
+static OFString NEMA_ENHANCED_CT_DIR = "/home/michael/data/dcm/nema_mf/DISCIMG/IMAGES/";
+static OFString SCAN_DUMP, DSET_DUMP;
+
+static void prepare_scan_dump();
+static void prepare_dset_dump();
+static void check_dump(const OFString& expected, const OFString& output);
+
+OFTEST(dcmfg_concatenation_loader)
+{
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
+    if (!OFStandard::dirExists(NEMA_ENHANCED_CT_DIR))
+        return;
+
+    prepare_scan_dump();
+    prepare_dset_dump();
+
+    // Scan directory and check that result is expected
+    ConcatenationLoader cl;
+    cl.setIgnoreMissingSourceUID(OFTrue); // NEMA test data misses this attribute...
+    OFCondition result = cl.scan(NEMA_ENHANCED_CT_DIR);
+    OFCHECK(result.good());
+    const ConcatenationLoader::TScanResult& concats = cl.getInfo();
+    OFCHECK(concats.size() == 3);
+    OFStringStream out;
+    ConcatenationLoader::TScanResult::const_iterator it = concats.begin();
+    while (it != concats.end())
+    {
+        (*it).second->print(out);
+        it++;
+        if (it != concats.end())
+        {
+            out << "--------------------------------------------------------------" << OFendl;
+        }
+    }
+    check_dump(SCAN_DUMP, out.str().c_str());
+
+    ConcatenationLoader::TScanFailures failed = cl.getFailedFiles();
+    ConcatenationLoader::TScanFailureIt ff    = failed.begin();
+    while (ff != failed.end())
+    {
+        // Filename is set
+        OFCHECK(!(*ff).fname.isEmpty());
+        // Error is set accordingly
+        OFCHECK((*ff).errorText == "File is not part of Concatenation");
+        // SOP Instance UID is set and valid
+        DcmUniqueIdentifier::checkStringValue((*ff).sopInstance, "1");
+        ff++;
+    }
+    // Scanning done, now load
+
+    DcmFileFormat dcmff;
+    OFVector<DcmIODTypes::Frame*> frames;
+    result = cl.load("1.3.6.1.4.1.5962.1.7.70.2.1.1166562673.14401", dcmff.getDataset(), frames);
+    OFCHECK(result.good());
+    if (result.good())
+    {
+        // Patch in expected values stored in pre-defined dump. In input concatenation,
+        // SOP Instance UID of Concatenation Source is missing so the conversion will create
+        // a new SOP Instance UID for the merged dataset.
+        OFCHECK(dcmff.getDataset()->putAndInsertOFStringArray(DCM_ContentDate, "20191009").good());
+        OFCHECK(dcmff.getDataset()->putAndInsertOFStringArray(DCM_ContentTime, "154326").good());
+        OFCHECK(dcmff.getDataset()
+                    ->putAndInsertOFStringArray(DCM_SOPInstanceUID, "1.3.6.1.4.1.5962.1.7.70.2.1.1166562673.14401")
+                    .good());
+        OFStringStream s;
+        dcmff.getDataset()->print(s);
+        check_dump(DSET_DUMP, s.str().c_str());
+    }
+
+    DcmIODUtil::freeContainer(frames);
+}
+
+static void prepare_scan_dump()
+{
+    SCAN_DUMP += "Concatenation UID*           : 1.3.6.1.4.1.5962.1.7.70.2.1.1166562673.14401\n";
+    SCAN_DUMP += "  SOP Class UID*             : 1.2.840.10008.5.1.4.1.1.2.1\n";
+    SCAN_DUMP += "  Concatentation Source UID* : \n";
+    SCAN_DUMP += "  Concatentation Source File : \n";
+    SCAN_DUMP += "  Number of Frames (computed): 60\n";
+    SCAN_DUMP += "  In-conc. Total Number      : 6\n";
+    SCAN_DUMP += "  Patient ID                 : 0070\n";
+    SCAN_DUMP += "  Study Instance UID*        : 1.3.6.1.4.1.5962.1.2.70.1166562673.14401\n";
+    SCAN_DUMP += "  Series Instance UID*       : 1.3.6.1.4.1.5962.1.3.70.2.1166562673.14401\n";
+    SCAN_DUMP += "  Bits Allocated*            : 16\n";
+    SCAN_DUMP += "  Rows*                      : 512\n";
+    SCAN_DUMP += "  Columns*                   : 512\n";
+    SCAN_DUMP += "  Files: \n";
+    SCAN_DUMP += "    1. /home/michael/data/dcm/nema_mf/DISCIMG/IMAGES/CT0074_1\n";
+    SCAN_DUMP += "    SOP Instance UID: 1.3.6.1.4.1.5962.1.1.70.2.1.1.1166562673.14401\n";
+    SCAN_DUMP += "    Number of Frames: 10\n";
+    SCAN_DUMP += "    In-Concatenation Frame Offset Number: 1\n";
+    SCAN_DUMP += "    2. /home/michael/data/dcm/nema_mf/DISCIMG/IMAGES/CT0074_2\n";
+    SCAN_DUMP += "    SOP Instance UID: 1.3.6.1.4.1.5962.1.1.70.2.1.2.1166562673.14401\n";
+    SCAN_DUMP += "    Number of Frames: 10\n";
+    SCAN_DUMP += "    In-Concatenation Frame Offset Number: 2\n";
+    SCAN_DUMP += "    3. /home/michael/data/dcm/nema_mf/DISCIMG/IMAGES/CT0074_3\n";
+    SCAN_DUMP += "    SOP Instance UID: 1.3.6.1.4.1.5962.1.1.70.2.1.3.1166562673.14401\n";
+    SCAN_DUMP += "    Number of Frames: 10\n";
+    SCAN_DUMP += "    In-Concatenation Frame Offset Number: 3\n";
+    SCAN_DUMP += "    4. /home/michael/data/dcm/nema_mf/DISCIMG/IMAGES/CT0074_4\n";
+    SCAN_DUMP += "    SOP Instance UID: 1.3.6.1.4.1.5962.1.1.70.2.1.4.1166562673.14401\n";
+    SCAN_DUMP += "    Number of Frames: 10\n";
+    SCAN_DUMP += "    In-Concatenation Frame Offset Number: 4\n";
+    SCAN_DUMP += "    5. /home/michael/data/dcm/nema_mf/DISCIMG/IMAGES/CT0074_5\n";
+    SCAN_DUMP += "    SOP Instance UID: 1.3.6.1.4.1.5962.1.1.70.2.1.5.1166562673.14401\n";
+    SCAN_DUMP += "    Number of Frames: 10\n";
+    SCAN_DUMP += "    In-Concatenation Frame Offset Number: 5\n";
+    SCAN_DUMP += "    6. /home/michael/data/dcm/nema_mf/DISCIMG/IMAGES/CT0074_6\n";
+    SCAN_DUMP += "    SOP Instance UID: 1.3.6.1.4.1.5962.1.1.70.2.1.6.1166562673.14401\n";
+    SCAN_DUMP += "    Number of Frames: 10\n";
+    SCAN_DUMP += "    In-Concatenation Frame Offset Number: 6\n";
+    SCAN_DUMP += "--------------------------------------------------------------\n";
+    SCAN_DUMP += "Concatenation UID*           : 1.3.6.1.4.1.5962.1.7.70.2.2.1166562673.14401\n";
+    SCAN_DUMP += "  SOP Class UID*             : 1.2.840.10008.5.1.4.1.1.2.1\n";
+    SCAN_DUMP += "  Concatentation Source UID* : \n";
+    SCAN_DUMP += "  Concatentation Source File : \n";
+    SCAN_DUMP += "  Number of Frames (computed): 30\n";
+    SCAN_DUMP += "  In-conc. Total Number      : 3\n";
+    SCAN_DUMP += "  Patient ID                 : 0070\n";
+    SCAN_DUMP += "  Study Instance UID*        : 1.3.6.1.4.1.5962.1.2.70.1166562673.14401\n";
+    SCAN_DUMP += "  Series Instance UID*       : 1.3.6.1.4.1.5962.1.3.70.2.1166562673.14401\n";
+    SCAN_DUMP += "  Bits Allocated*            : 16\n";
+    SCAN_DUMP += "  Rows*                      : 512\n";
+    SCAN_DUMP += "  Columns*                   : 512\n";
+    SCAN_DUMP += "  Files: \n";
+    SCAN_DUMP += "    1. /home/michael/data/dcm/nema_mf/DISCIMG/IMAGES/CT0075_1\n";
+    SCAN_DUMP += "    SOP Instance UID: 1.3.6.1.4.1.5962.1.1.70.2.2.1.1166562673.14401\n";
+    SCAN_DUMP += "    Number of Frames: 10\n";
+    SCAN_DUMP += "    In-Concatenation Frame Offset Number: 1\n";
+    SCAN_DUMP += "    2. /home/michael/data/dcm/nema_mf/DISCIMG/IMAGES/CT0075_2\n";
+    SCAN_DUMP += "    SOP Instance UID: 1.3.6.1.4.1.5962.1.1.70.2.2.2.1166562673.14401\n";
+    SCAN_DUMP += "    Number of Frames: 10\n";
+    SCAN_DUMP += "    In-Concatenation Frame Offset Number: 2\n";
+    SCAN_DUMP += "    3. /home/michael/data/dcm/nema_mf/DISCIMG/IMAGES/CT0075_3\n";
+    SCAN_DUMP += "    SOP Instance UID: 1.3.6.1.4.1.5962.1.1.70.2.2.3.1166562673.14401\n";
+    SCAN_DUMP += "    Number of Frames: 10\n";
+    SCAN_DUMP += "    In-Concatenation Frame Offset Number: 3\n";
+    SCAN_DUMP += "--------------------------------------------------------------\n";
+    SCAN_DUMP += "Concatenation UID*           : 1.3.6.1.4.1.5962.1.7.70.2.3.1166562673.14401\n";
+    SCAN_DUMP += "  SOP Class UID*             : 1.2.840.10008.5.1.4.1.1.2.1\n";
+    SCAN_DUMP += "  Concatentation Source UID* : \n";
+    SCAN_DUMP += "  Concatentation Source File : \n";
+    SCAN_DUMP += "  Number of Frames (computed): 30\n";
+    SCAN_DUMP += "  In-conc. Total Number      : 3\n";
+    SCAN_DUMP += "  Patient ID                 : 0070\n";
+    SCAN_DUMP += "  Study Instance UID*        : 1.3.6.1.4.1.5962.1.2.70.1166562673.14401\n";
+    SCAN_DUMP += "  Series Instance UID*       : 1.3.6.1.4.1.5962.1.3.70.2.1166562673.14401\n";
+    SCAN_DUMP += "  Bits Allocated*            : 16\n";
+    SCAN_DUMP += "  Rows*                      : 512\n";
+    SCAN_DUMP += "  Columns*                   : 512\n";
+    SCAN_DUMP += "  Files: \n";
+    SCAN_DUMP += "    1. /home/michael/data/dcm/nema_mf/DISCIMG/IMAGES/CT0076_1\n";
+    SCAN_DUMP += "    SOP Instance UID: 1.3.6.1.4.1.5962.1.1.70.2.3.1.1166562673.14401\n";
+    SCAN_DUMP += "    Number of Frames: 10\n";
+    SCAN_DUMP += "    In-Concatenation Frame Offset Number: 1\n";
+    SCAN_DUMP += "    2. /home/michael/data/dcm/nema_mf/DISCIMG/IMAGES/CT0076_2\n";
+    SCAN_DUMP += "    SOP Instance UID: 1.3.6.1.4.1.5962.1.1.70.2.3.2.1166562673.14401\n";
+    SCAN_DUMP += "    Number of Frames: 10\n";
+    SCAN_DUMP += "    In-Concatenation Frame Offset Number: 2\n";
+    SCAN_DUMP += "    3. /home/michael/data/dcm/nema_mf/DISCIMG/IMAGES/CT0076_3\n";
+    SCAN_DUMP += "    SOP Instance UID: 1.3.6.1.4.1.5962.1.1.70.2.3.3.1166562673.14401\n";
+    SCAN_DUMP += "    Number of Frames: 10\n";
+    SCAN_DUMP += "    In-Concatenation Frame Offset Number: 3\n";
+
+    OFStringUtil::replace_all(SCAN_DUMP, "/home/michael/data/dcm/nema_mf/DISCIMG/IMAGES/", NEMA_ENHANCED_CT_DIR);
+}
+
+static void prepare_dset_dump()
+{
+    DSET_DUMP += "\n";
+    DSET_DUMP += "# Dicom-Data-Set\n";
+    DSET_DUMP += "# Used TransferSyntax: Little Endian Explicit\n";
+    DSET_DUMP += "(0008,0005) CS [ISO_IR 100]                             #  10, 1 SpecificCharacterSet\n";
+    DSET_DUMP += "(0008,0008) CS [ORIGINAL\\PRIMARY\\POST_CONTRAST\\NONE]    #  36, 4 ImageType\n";
+    DSET_DUMP += "(0008,0012) DA [20061219]                               #   8, 1 InstanceCreationDate\n";
+    DSET_DUMP += "(0008,0013) TM [205025]                                 #   6, 1 InstanceCreationTime\n";
+    DSET_DUMP += "(0008,0014) UI [1.3.6.1.4.1.5962.3]                     #  18, 1 InstanceCreatorUID\n";
+    DSET_DUMP += "(0008,0016) UI =EnhancedCTImageStorage                  #  28, 1 SOPClassUID\n";
+    DSET_DUMP += "(0008,0018) UI [1.3.6.1.4.1.5962.1.7.70.2.1.1166562673.14401] #  44, 1 SOPInstanceUID\n";
+    DSET_DUMP += "(0008,0020) DA [20061219]                               #   8, 1 StudyDate\n";
+    DSET_DUMP += "(0008,0021) DA [20061219]                               #   8, 1 SeriesDate\n";
+    DSET_DUMP += "(0008,0023) DA [20191009]                               #   8, 1 ContentDate\n";
+    DSET_DUMP += "(0008,002a) DT [20061219204055]                         #  14, 1 AcquisitionDateTime\n";
+    DSET_DUMP += "(0008,0030) TM [203523]                                 #   6, 1 StudyTime\n";
+    DSET_DUMP += "(0008,0031) TM [204010]                                 #   6, 1 SeriesTime\n";
+    DSET_DUMP += "(0008,0033) TM [154326]                                 #   6, 1 ContentTime\n";
+    DSET_DUMP += "(0008,0050) SH [0070]                                   #   4, 1 AccessionNumber\n";
+    DSET_DUMP += "(0008,0060) CS [CT]                                     #   2, 1 Modality\n";
+    DSET_DUMP += "(0008,0070) LO [Acme Medical Devices]                   #  20, 1 Manufacturer\n";
+    DSET_DUMP += "(0008,0080) LO [St. Nowhere Hospital]                   #  20, 1 InstitutionName\n";
+    DSET_DUMP += "(0008,0090) PN [Thomas^Albert]                          #  14, 1 ReferringPhysicianName\n";
+    DSET_DUMP += "(0008,0201) SH [-0400]                                  #   6, 1 TimezoneOffsetFromUTC\n";
+    DSET_DUMP += "(0008,1010) SH [CONSOLE01]                              #  10, 1 StationName\n";
+    DSET_DUMP += "(0008,1030) LO (no value available)                     #   0, 0 StudyDescription\n";
+    DSET_DUMP += "(0008,103e) LO [Shared dimensions and stacks across series and concatenations] #  62, 1 "
+                 "SeriesDescription\n";
+    DSET_DUMP += "(0008,1050) PN [Smith^John]                             #  10, 1 PerformingPhysicianName\n";
+    DSET_DUMP += "(0008,1060) PN [Smith^John]                             #  10, 1 NameOfPhysiciansReadingStudy\n";
+    DSET_DUMP += "(0008,1070) PN [Jones^Molly]                            #  12, 1 OperatorsName\n";
+    DSET_DUMP += "(0008,1090) LO [Super Dooper Scanner]                   #  20, 1 ManufacturerModelName\n";
+    DSET_DUMP += "(0008,9121) SQ (Sequence with undefined length #=1)     # u/l, 1 ReferencedRawDataSequence\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=2)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0008,1115) SQ (Sequence with undefined length #=1)     # u/l, 1 ReferencedSeriesSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=2)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0008,1199) SQ (Sequence with undefined length #=1)     # u/l, 1 ReferencedSOPSequence\n";
+    DSET_DUMP += "          (fffe,e000) na (Item with undefined length #=2)         # u/l, 1 Item\n";
+    DSET_DUMP += "            (0008,1150) UI =RawDataStorage                          #  26, 1 ReferencedSOPClassUID\n";
+    DSET_DUMP += "            (0008,1155) UI [1.3.6.1.4.1.5962.1.9.70.2.1166562673.14401] #  42, 1 "
+                 "ReferencedSOPInstanceUID\n";
+    DSET_DUMP += "          (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "        (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "        (0020,000e) UI [1.3.6.1.4.1.5962.1.3.70.2.1166562673.14401] #  42, 1 SeriesInstanceUID\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,000d) UI [1.3.6.1.4.1.5962.1.2.70.1166562673.14401] #  40, 1 StudyInstanceUID\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "(0008,9205) CS [MONOCHROME]                             #  10, 1 PixelPresentation\n";
+    DSET_DUMP += "(0008,9206) CS [VOLUME]                                 #   6, 1 VolumetricProperties\n";
+    DSET_DUMP += "(0008,9207) CS [NONE]                                   #   4, 1 VolumeBasedCalculationTechnique\n";
+    DSET_DUMP += "(0010,0010) PN [ChestAbdoPelvis^MultiphaseLiver]        #  32, 1 PatientName\n";
+    DSET_DUMP += "(0010,0020) LO [0070]                                   #   4, 1 PatientID\n";
+    DSET_DUMP += "(0010,0030) DA [19500704]                               #   8, 1 PatientBirthDate\n";
+    DSET_DUMP += "(0010,0040) CS [M]                                      #   2, 1 PatientSex\n";
+    DSET_DUMP += "(0010,1010) AS [052Y]                                   #   4, 1 PatientAge\n";
+    DSET_DUMP += "(0010,1020) DS [1.6]                                    #   4, 1 PatientSize\n";
+    DSET_DUMP += "(0010,1030) DS [75]                                     #   2, 1 PatientWeight\n";
+    DSET_DUMP += "(0018,0012) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusAgentSequence\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=8)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0008,0100) SH [C-B0322]                                #   8, 1 CodeValue\n";
+    DSET_DUMP += "    (0008,0102) SH [SRT]                                    #   4, 1 CodingSchemeDesignator\n";
+    DSET_DUMP += "    (0008,0104) LO [Iohexol]                                #   8, 1 CodeMeaning\n";
+    DSET_DUMP += "    (0018,0014) SQ (Sequence with undefined length #=1)     # u/l, 1 "
+                 "ContrastBolusAdministrationRouteSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0008,0100) SH [G-D101]                                 #   6, 1 CodeValue\n";
+    DSET_DUMP += "        (0008,0102) SH [SNM3]                                   #   4, 1 CodingSchemeDesignator\n";
+    DSET_DUMP += "        (0008,0104) LO [Intravenous route]                      #  18, 1 CodeMeaning\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,1041) DS [150]                                    #   4, 1 ContrastBolusVolume\n";
+    DSET_DUMP += "    (0018,1049) DS [300]                                    #   4, 1 "
+                 "ContrastBolusIngredientConcentration\n";
+    DSET_DUMP += "    (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "    (0018,9338) SQ (Sequence with undefined length #=1)     # u/l, 1 ContrastBolusIngredientCodeSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0008,0100) SH [C-11400]                                #   8, 1 CodeValue\n";
+    DSET_DUMP += "        (0008,0102) SH [SRT]                                    #   4, 1 CodingSchemeDesignator\n";
+    DSET_DUMP += "        (0008,0104) LO [Iodine]                                 #   6, 1 CodeMeaning\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=8)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0008,0100) SH [C-B0317]                                #   8, 1 CodeValue\n";
+    DSET_DUMP += "    (0008,0102) SH [SNM3]                                   #   4, 1 CodingSchemeDesignator\n";
+    DSET_DUMP += "    (0008,0104) LO [Diatrizoate]                            #  12, 1 CodeMeaning\n";
+    DSET_DUMP += "    (0018,0014) SQ (Sequence with undefined length #=1)     # u/l, 1 "
+                 "ContrastBolusAdministrationRouteSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0008,0100) SH [G-D140]                                 #   6, 1 CodeValue\n";
+    DSET_DUMP += "        (0008,0102) SH [SNM3]                                   #   4, 1 CodingSchemeDesignator\n";
+    DSET_DUMP += "        (0008,0104) LO [Oral route]                             #  10, 1 CodeMeaning\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,1041) DS [1000]                                   #   4, 1 ContrastBolusVolume\n";
+    DSET_DUMP += "    (0018,1049) DS [11.1]                                   #   4, 1 "
+                 "ContrastBolusIngredientConcentration\n";
+    DSET_DUMP += "    (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "    (0018,9338) SQ (Sequence with undefined length #=1)     # u/l, 1 ContrastBolusIngredientCodeSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0008,0100) SH [C-11400]                                #   8, 1 CodeValue\n";
+    DSET_DUMP += "        (0008,0102) SH [SRT]                                    #   4, 1 CodingSchemeDesignator\n";
+    DSET_DUMP += "        (0008,0104) LO [Iodine]                                 #   6, 1 CodeMeaning\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "(0018,1000) LO [123456]                                 #   6, 1 DeviceSerialNumber\n";
+    DSET_DUMP += "(0018,1020) LO [1.00]                                   #   4, 1 SoftwareVersions\n";
+    DSET_DUMP += "(0018,5100) CS [FFS]                                    #   4, 1 PatientPosition\n";
+    DSET_DUMP += "(0018,9004) CS [PRODUCT]                                #   8, 1 ContentQualification\n";
+    DSET_DUMP += "(0018,9073) FD 522.00048828124988631                    #   8, 1 AcquisitionDuration\n";
+    DSET_DUMP += "(0020,000d) UI [1.3.6.1.4.1.5962.1.2.70.1166562673.14401] #  40, 1 StudyInstanceUID\n";
+    DSET_DUMP += "(0020,000e) UI [1.3.6.1.4.1.5962.1.3.70.2.1166562673.14401] #  42, 1 SeriesInstanceUID\n";
+    DSET_DUMP += "(0020,0010) SH [0070]                                   #   4, 1 StudyID\n";
+    DSET_DUMP += "(0020,0011) IS [2]                                      #   2, 1 SeriesNumber\n";
+    DSET_DUMP += "(0020,0012) IS [2]                                      #   2, 1 AcquisitionNumber\n";
+    DSET_DUMP += "(0020,0013) IS [1]                                      #   2, 1 InstanceNumber\n";
+    DSET_DUMP += "(0020,0052) UI [1.3.6.1.4.1.5962.1.4.70.1.1166562673.14401] #  42, 1 FrameOfReferenceUID\n";
+    DSET_DUMP += "(0020,1040) LO [XY]                                     #   2, 1 PositionReferenceIndicator\n";
+    DSET_DUMP += "(0020,4000) LT [Both arterial and portal venous]        #  32, 1 ImageComments\n";
+    DSET_DUMP += "(0020,9221) SQ (Sequence with undefined length #=1)     # u/l, 1 DimensionOrganizationSequence\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP
+        += "    (0020,9164) UI [1.3.6.1.4.1.5962.1.6.70.2.0.1166562673.14401] #  44, 1 DimensionOrganizationUID\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "(0020,9222) SQ (Sequence with undefined length #=3)     # u/l, 1 DimensionIndexSequence\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP
+        += "    (0020,9164) UI [1.3.6.1.4.1.5962.1.6.70.2.0.1166562673.14401] #  44, 1 DimensionOrganizationUID\n";
+    DSET_DUMP += "    (0020,9165) AT (0020,9056)                              #   4, 1 DimensionIndexPointer\n";
+    DSET_DUMP += "    (0020,9167) AT (0020,9111)                              #   4, 1 FunctionalGroupPointer\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP
+        += "    (0020,9164) UI [1.3.6.1.4.1.5962.1.6.70.2.0.1166562673.14401] #  44, 1 DimensionOrganizationUID\n";
+    DSET_DUMP += "    (0020,9165) AT (0020,9057)                              #   4, 1 DimensionIndexPointer\n";
+    DSET_DUMP += "    (0020,9167) AT (0020,9111)                              #   4, 1 FunctionalGroupPointer\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP
+        += "    (0020,9164) UI [1.3.6.1.4.1.5962.1.6.70.2.0.1166562673.14401] #  44, 1 DimensionOrganizationUID\n";
+    DSET_DUMP += "    (0020,9165) AT (0018,9344)                              #   4, 1 DimensionIndexPointer\n";
+    DSET_DUMP += "    (0020,9167) AT (0018,9341)                              #   4, 1 FunctionalGroupPointer\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "(0028,0002) US 1                                        #   2, 1 SamplesPerPixel\n";
+    DSET_DUMP += "(0028,0004) CS [MONOCHROME2]                            #  12, 1 PhotometricInterpretation\n";
+    DSET_DUMP += "(0028,0008) IS [60]                                     #   2, 1 NumberOfFrames\n";
+    DSET_DUMP += "(0028,0010) US 512                                      #   2, 1 Rows\n";
+    DSET_DUMP += "(0028,0011) US 512                                      #   2, 1 Columns\n";
+    DSET_DUMP += "(0028,0100) US 16                                       #   2, 1 BitsAllocated\n";
+    DSET_DUMP += "(0028,0101) US 16                                       #   2, 1 BitsStored\n";
+    DSET_DUMP += "(0028,0102) US 15                                       #   2, 1 HighBit\n";
+    DSET_DUMP += "(0028,0103) US 1                                        #   2, 1 PixelRepresentation\n";
+    DSET_DUMP += "(0028,0301) CS [NO]                                     #   2, 1 BurnedInAnnotation\n";
+    DSET_DUMP += "(0028,2110) CS [00]                                     #   2, 1 LossyImageCompression\n";
+    DSET_DUMP += "(0040,0555) SQ (Sequence with undefined length #=0)     # u/l, 1 AcquisitionContextSequence\n";
+    DSET_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "(2050,0020) CS [IDENTITY]                               #   8, 1 PresentationLUTShape\n";
+    DSET_DUMP += "(5200,9229) SQ (Sequence with undefined length #=1)     # u/l, 1 SharedFunctionalGroupsSequence\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=14)        # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9301) SQ (Sequence with undefined length #=1)     # u/l, 1 CTAcquisitionTypeSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9302) CS [SPIRAL]                                 #   6, 1 AcquisitionType\n";
+    DSET_DUMP += "        (0018,9333) CS [NO]                                     #   2, 1 ConstantVolumeFlag\n";
+    DSET_DUMP += "        (0018,9334) CS [NO]                                     #   2, 1 FluoroscopyFlag\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9304) SQ (Sequence with undefined length #=1)     # u/l, 1 CTAcquisitionDetailsSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,0090) DS [480.000]                                #   8, 1 DataCollectionDiameter\n";
+    DSET_DUMP += "        (0018,1120) DS [0.00000]                                #   8, 1 GantryDetectorTilt\n";
+    DSET_DUMP += "        (0018,1130) DS [103.200]                                #   8, 1 TableHeight\n";
+    DSET_DUMP += "        (0018,1140) CS [CW]                                     #   2, 1 RotationDirection\n";
+    DSET_DUMP += "        (0018,9305) FD 1                                        #   8, 1 RevolutionTime\n";
+    DSET_DUMP += "        (0018,9306) FD 7.000007629394530361822                  #   8, 1 SingleCollimationWidth\n";
+    DSET_DUMP += "        (0018,9307) FD 7.000007629394530361822                  #   8, 1 TotalCollimationWidth\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9308) SQ (Sequence with undefined length #=1)     # u/l, 1 CTTableDynamicsSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9309) FD 9.8000183105468732                       #   8, 1 TableSpeed\n";
+    DSET_DUMP += "        (0018,9310) FD 9.800010681152342                        #   8, 1 TableFeedPerRotation\n";
+    DSET_DUMP += "        (0018,9311) FD 1.4000015258789061                       #   8, 1 SpiralPitchFactor\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9312) SQ (Sequence with undefined length #=1)     # u/l, 1 CTGeometrySequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=2)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,1110) DS [1099.31]                                #   8, 1 DistanceSourceToDetector\n";
+    DSET_DUMP += "        (0018,9335) FD 630.00048828124988631                    #   8, 1 "
+                 "DistanceSourceToDataCollectionCenter\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9314) SQ (Sequence with undefined length #=1)     # u/l, 1 CTReconstructionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,1100) DS [325.000]                                #   8, 1 ReconstructionDiameter\n";
+    DSET_DUMP += "        (0018,1210) SH [STANDARD]                               #   8, 1 ConvolutionKernel\n";
+    DSET_DUMP += "        (0018,9315) CS [ITERATIVE]                              #  10, 1 ReconstructionAlgorithm\n";
+    DSET_DUMP += "        (0018,9316) CS [SOFT_TISSUE]                            #  12, 1 ConvolutionKernelGroup\n";
+    DSET_DUMP += "        (0018,9319) FD 360.00024414062494316                    #   8, 1 ReconstructionAngle\n";
+    DSET_DUMP += "        (0018,9320) SH [None]                                   #   4, 1 ImageFilter\n";
+    DSET_DUMP
+        += "        (0018,9322) FD 0.63476610183715811\\0.63476610183715811  #  16, 2 ReconstructionPixelSpacing\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9321) SQ (Sequence with undefined length #=1)     # u/l, 1 CTExposureSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=5)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9323) CS [NONE]                                   #   4, 1 ExposureModulationType\n";
+    DSET_DUMP += "        (0018,9328) FD 1000.0004882812498863                    #   8, 1 ExposureTimeInms\n";
+    DSET_DUMP += "        (0018,9330) FD 230.00012207031247158                    #   8, 1 XRayTubeCurrentInmA\n";
+    DSET_DUMP += "        (0018,9332) FD 230.00012207031247158                    #   8, 1 ExposureInmAs\n";
+    DSET_DUMP += "        (0018,9345) FD (no value available)                     #   0, 0 CTDIvol\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9325) SQ (Sequence with undefined length #=1)     # u/l, 1 CTXRayDetailsSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,0060) DS [120.000]                                #   8, 1 KVP\n";
+    DSET_DUMP += "        (0018,1160) SH [WEDGE]                                  #   6, 1 FilterType\n";
+    DSET_DUMP += "        (0018,1190) DS [1.20000]                                #   8, 1 FocalSpots\n";
+    DSET_DUMP += "        (0018,7050) CS [MIXED]                                  #   6, 1 FilterMaterial\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9329) SQ (Sequence with undefined length #=1)     # u/l, 1 CTImageFrameTypeSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0008,9007) CS [ORIGINAL\\PRIMARY\\POST_CONTRAST\\NONE]    #  36, 4 FrameType\n";
+    DSET_DUMP += "        (0008,9205) CS [MONOCHROME]                             #  10, 1 PixelPresentation\n";
+    DSET_DUMP += "        (0008,9206) CS [VOLUME]                                 #   6, 1 VolumetricProperties\n";
+    DSET_DUMP
+        += "        (0008,9207) CS [NONE]                                   #   4, 1 VolumeBasedCalculationTechnique\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9477) SQ (Sequence with undefined length #=1)     # u/l, 1 "
+                 "IrradiationEventIdentificationSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP
+        += "        (0008,3010) UI [1.3.6.1.4.1.5962.1.10.70.2.1.1166562673.14401] #  46, 1 IrradiationEventUID\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9071) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameAnatomySequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=2)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0008,2218) SQ (Sequence with undefined length #=1)     # u/l, 1 AnatomicRegionSequence\n";
+    DSET_DUMP += "          (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "            (0008,0100) SH [R-FAB57]                                #   8, 1 CodeValue\n";
+    DSET_DUMP
+        += "            (0008,0102) SH [SRT]                                    #   4, 1 CodingSchemeDesignator\n";
+    DSET_DUMP += "            (0008,0104) LO [Abdomen and Pelvis]                     #  18, 1 CodeMeaning\n";
+    DSET_DUMP += "          (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "        (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "        (0020,9072) CS [U]                                      #   2, 1 FrameLaterality\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9116) SQ (Sequence with undefined length #=1)     # u/l, 1 PlaneOrientationSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0037) DS [1.00000\\0.00000\\0.00000\\0.00000\\1.00000\\0.00000] #  48, 6 "
+                 "ImageOrientationPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0028,9110) SQ (Sequence with undefined length #=1)     # u/l, 1 PixelMeasuresSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=2)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,0050) DS [7.00000]                                #   8, 1 SliceThickness\n";
+    DSET_DUMP += "        (0028,0030) DS [0.634766\\0.634766]                      #  18, 2 PixelSpacing\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0028,9132) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameVOILUTSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=2)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0028,1050) DS [40.0000]                                #   8, 1 WindowCenter\n";
+    DSET_DUMP += "        (0028,1051) DS [400.000]                                #   8, 1 WindowWidth\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP
+        += "    (0028,9145) SQ (Sequence with undefined length #=1)     # u/l, 1 PixelValueTransformationSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0028,1052) DS [-1024.00]                               #   8, 1 RescaleIntercept\n";
+    DSET_DUMP += "        (0028,1053) DS [1.00000]                                #   8, 1 RescaleSlope\n";
+    DSET_DUMP += "        (0028,1054) LO [HU]                                     #   2, 1 RescaleType\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "(5200,9230) SQ (Sequence with undefined length #=60)    # u/l, 1 PerFrameFunctionalGroupsSequence\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-10.00000762939452947364 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-10.00000762939452947364 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -10.00000762939452947364                 #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204055]                         #  14, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204055.350]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 30                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\30\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-10.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-17.0000152587890589473 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-17.0000152587890589473 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -17.00143432617187145                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204055.714]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204056.064]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 29                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\29\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-17.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-24.0000152587890589473 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-24.0000152587890589473 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -24.00285339355468395                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204056.428]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204056.778]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 28                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\28\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-24.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-31.0000152587890589473 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-31.0000152587890589473 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -31.00427246093749645                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204057.142]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204057.492]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 27                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\27\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-31.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-38.0000305175781178946 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-38.0000305175781178946 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -37.995758056640618                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204057.857]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204058.207]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 26                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\26\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-38.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-45.0000305175781178946 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-45.0000305175781178946 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -44.997161865234368                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204058.571]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204058.921]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 25                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\25\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-45.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-52.0000305175781178946 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-52.0000305175781178946 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -51.998596191406243                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204059.285]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204059.635]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 24                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\24\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-52.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-59.0000305175781178946 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-59.0000305175781178946 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -59.0000305175781178946                  #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204100]                         #  14, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204100.350]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 23                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\23\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-59.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-66.0000610351562357891 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-66.0000610351562357891 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -66.00146484374998579                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204100.714]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204101.064]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 22                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\22\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-66.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-73.0000610351562357891 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-73.0000610351562357891 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -73.00286865234373579                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204101.428]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204101.778]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 21                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\21\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-73.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-80.0000610351562357891 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-80.0000610351562357891 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -80.00433349609373579                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204102.142]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204102.492]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 20                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\20\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-80.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-87.0000610351562357891 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-87.0000610351562357891 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -86.995788574218736                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204102.857]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204103.207]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 19                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\19\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-87.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-94.0000610351562357891 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-94.0000610351562357891 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -93.997192382812486                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204103.571]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204103.921]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 18                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\18\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-94.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-101.000061035156235789 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-101.000061035156235789 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -100.99859619140624                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204104.285]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204104.635]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 17                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\17\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-101.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-108.000061035156235789 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-108.000061035156235789 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -108.000061035156235789                  #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204105]                         #  14, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204105.350]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 16                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\16\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-108.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-115.000061035156235789 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-115.000061035156235789 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -115.0014648437499858                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204105.714]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204106.064]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 15                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\15\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-115.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-122.000061035156235789 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-122.000061035156235789 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -122.0028686523437358                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204106.428]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204106.778]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 14                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\14\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-122.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-129.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-129.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -129.0043945312499716                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204107.142]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204107.492]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 13                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\13\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-129.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-136.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-136.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -135.99584960937497                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204107.857]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204108.207]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 12                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\12\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-136.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-143.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-143.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -142.99719238281247                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204108.571]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204108.921]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 11                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\11\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-143.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-150.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-150.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -149.99865722656247                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204109.285]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204109.635]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 10                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\10\\1                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-150.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-157.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-157.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -157.00012207031247158                   #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204109.999]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204110.349]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 9                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\9\\1                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-157.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-164.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-164.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -164.0014648437499716                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204110.714]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204111.064]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 8                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\8\\1                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-164.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-171.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-171.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -171.0029296874999716                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204111.428]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204111.778]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 7                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\7\\1                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-171.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-178.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-178.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -178.0043945312499716                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204112.142]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204112.492]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 6                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\6\\1                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-178.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-185.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-185.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -184.99584960937497                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204112.857]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204113.207]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 5                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\5\\1                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-185.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-192.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-192.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -191.99719238281247                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204113.571]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204113.921]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 4                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\4\\1                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-192.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-199.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-199.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -198.99865722656247                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204114.285]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204114.635]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 3                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\3\\1                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-199.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-206.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-206.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -206.00012207031247158                   #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204115]                         #  14, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204115.350]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 2                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\2\\1                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-206.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-213.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-213.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -213.0014648437499716                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [ARTERIAL]                               #   8, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204115.714]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204116.064]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 1                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\1\\1                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-213.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-10.00000762939452947364 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-10.00000762939452947364 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -10.00000762939452947364                 #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204137]                         #  14, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204137.350]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 30                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\30\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-10.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-17.0000152587890589473 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-17.0000152587890589473 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -17.00143432617187145                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204137.714]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204138.064]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 29                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\29\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-17.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-24.0000152587890589473 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-24.0000152587890589473 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -24.00285339355468395                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204138.428]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204138.778]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 28                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\28\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-24.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-31.0000152587890589473 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-31.0000152587890589473 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -31.00427246093749645                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204139.142]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204139.492]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 27                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\27\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-31.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-38.0000305175781178946 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-38.0000305175781178946 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -37.995758056640618                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204139.857]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204140.207]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 26                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\26\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-38.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-45.0000305175781178946 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-45.0000305175781178946 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -44.997161865234368                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204140.571]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204140.921]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 25                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\25\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-45.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-52.0000305175781178946 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-52.0000305175781178946 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -51.998596191406243                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204141.285]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204141.635]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 24                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\24\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-52.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-59.0000305175781178946 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-59.0000305175781178946 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -59.0000305175781178946                  #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204142]                         #  14, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204142.350]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 23                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\23\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-59.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-66.0000610351562357891 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-66.0000610351562357891 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -66.00146484374998579                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204142.714]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204143.064]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 22                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\22\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-66.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-73.0000610351562357891 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-73.0000610351562357891 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -73.00286865234373579                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204143.428]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204143.778]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 21                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\21\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-73.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-80.0000610351562357891 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-80.0000610351562357891 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -80.00433349609373579                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204144.142]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204144.492]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 20                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\20\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-80.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-87.0000610351562357891 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-87.0000610351562357891 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -86.995788574218736                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204144.857]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204145.207]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 19                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\19\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-87.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-94.0000610351562357891 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-94.0000610351562357891 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -93.997192382812486                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204145.571]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204145.921]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 18                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\18\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-94.0000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-101.000061035156235789 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-101.000061035156235789 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -100.99859619140624                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204146.285]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204146.635]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 17                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\17\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-101.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-108.000061035156235789 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-108.000061035156235789 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -108.000061035156235789                  #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204147]                         #  14, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204147.350]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 16                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\16\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-108.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-115.000061035156235789 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-115.000061035156235789 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -115.0014648437499858                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204147.714]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204148.064]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 15                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\15\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-115.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-122.000061035156235789 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-122.000061035156235789 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -122.0028686523437358                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204148.428]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204148.778]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 14                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\14\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-122.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-129.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-129.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -129.0043945312499716                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204149.142]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204149.492]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 13                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\13\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-129.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-136.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-136.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -135.99584960937497                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204149.857]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204150.207]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 12                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\12\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-136.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-143.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-143.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -142.99719238281247                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204150.571]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204150.921]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 11                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\11\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-143.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-150.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-150.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -149.99865722656247                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204151.285]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204151.635]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 10                                       #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\10\\2                                   #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-150.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-157.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-157.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -157.00012207031247158                   #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204151.999]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204152.349]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 9                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\9\\2                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-157.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-164.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-164.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -164.0014648437499716                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204152.714]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204153.064]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 8                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\8\\2                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-164.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-171.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-171.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -171.0029296874999716                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204153.428]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204153.778]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 7                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\7\\2                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-171.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-178.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-178.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -178.0043945312499716                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204154.142]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204154.492]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 6                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\6\\2                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-178.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-185.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-185.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -184.99584960937497                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204154.857]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204155.207]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 5                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\5\\2                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-185.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-192.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-192.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -191.99719238281247                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204155.571]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204155.921]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 4                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\4\\2                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-192.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-199.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-199.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -198.99865722656247                      #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204156.285]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204156.635]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 3                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\3\\2                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-199.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-206.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-206.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -206.00012207031247158                   #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204157]                         #  14, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204157.350]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 2                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\2\\2                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-206.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "    (0018,9326) SQ (Sequence with undefined length #=1)     # u/l, 1 CTPositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9313) FD 3.08271408081054643\\-0.31728720664978023\\-213.00012207031247158 #  24, 3 "
+                 "DataCollectionCenterPatient\n";
+    DSET_DUMP += "        (0018,9318) FD 3.08271408081054643\\-0.31728720664978023\\-213.00012207031247158 #  24, 3 "
+                 "ReconstructionTargetCenterPatient\n";
+    DSET_DUMP += "        (0018,9327) FD -213.0014648437499716                    #   8, 1 TablePosition\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0018,9341) SQ (Sequence with undefined length #=2)     # u/l, 1 ContrastBolusUsageSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=4)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 1                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS [YES]                                    #   4, 1 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "        (0018,9344) CS [PORTAL_VENOUS]                          #  14, 1 ContrastBolusAgentPhase\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=3)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9337) US 2                                        #   2, 1 ContrastBolusAgentNumber\n";
+    DSET_DUMP
+        += "        (0018,9342) CS [YES]                                    #   4, 1 ContrastBolusAgentAdministered\n";
+    DSET_DUMP
+        += "        (0018,9343) CS (no value available)                     #   0, 0 ContrastBolusAgentDetected\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9111) SQ (Sequence with undefined length #=1)     # u/l, 1 FrameContentSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=7)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0018,9074) DT [20061219204157.714]                     #  18, 1 FrameAcquisitionDateTime\n";
+    DSET_DUMP += "        (0018,9151) DT [20061219204158.064]                     #  18, 1 FrameReferenceDateTime\n";
+    DSET_DUMP += "        (0018,9220) FD 700.00048828124988631                    #   8, 1 FrameAcquisitionDuration\n";
+    DSET_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    DSET_DUMP += "        (0020,9057) UL 1                                        #   4, 1 InStackPositionNumber\n";
+    DSET_DUMP += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    DSET_DUMP += "        (0020,9157) UL 1\\1\\2                                    #  12, 3 DimensionIndexValues\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "    (0020,9113) SQ (Sequence with undefined length #=1)     # u/l, 1 PlanePositionSequence\n";
+    DSET_DUMP += "      (fffe,e000) na (Item with undefined length #=1)         # u/l, 1 Item\n";
+    DSET_DUMP += "        (0020,0032) DS [-159.100\\-162.500\\-213.000]             #  26, 3 ImagePositionPatient\n";
+    DSET_DUMP += "      (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+    DSET_DUMP += "  (fffe,e00d) na (ItemDelimitationItem)                   #   0, 0 ItemDelimitationItem\n";
+    DSET_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem)               #   0, 0 SequenceDelimitationItem\n";
+}
+
+void check_dump(const OFString& expected, const OFString& output)
+{
+    OFBool matches = (expected == output);
+    OFCHECK(matches);
+    if (!matches)
+    {
+        CERR << "Expected dump:" << OFendl;
+        CERR << expected << OFendl;
+        CERR << "Produced dump:" << OFendl;
+        CERR << output << OFendl;
+    }
+}
diff --git a/dcmfg/tests/t_ct_acquisition_details.cc b/dcmfg/tests/t_ct_acquisition_details.cc
new file mode 100644 (file)
index 0000000..1ee03ee
--- /dev/null
@@ -0,0 +1,211 @@
+/*
+ *
+ *  Copyright (C) 2019-2020, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Tests for CT Acquisition Type FG class
+ *
+ */
+
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+
+#include "dcmtk/dcmfg/fgctacquisitiondetails.h"
+#include "dcmtk/dcmfg/fginterface.h"
+#include "dcmtk/ofstd/ofcond.h"
+#include "dcmtk/ofstd/oftest.h"
+
+static void checkDump(const OFString& ds_dump, const OFString& expected_dump);
+
+static void init_template(OFString& fg_dump)
+{
+    fg_dump += "(fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    fg_dump += "(0018,9304) SQ (Sequence with explicit length #=2)      #   0, 1 CTAcquisitionDetailsSequence\n";
+    fg_dump += "  (fffe,e000) na (Item with explicit length #=8)          #   0, 1 Item\n";
+    fg_dump += "    (0018,0090) DS [6]                                      #   2, 1 DataCollectionDiameter\n";
+    fg_dump += "    (0018,1120) DS [5]                                      #   2, 1 GantryDetectorTilt\n";
+    fg_dump += "    (0018,1130) DS [4]                                      #   2, 1 TableHeight\n";
+    fg_dump += "    (0018,1140) CS [CC]                                     #   2, 1 RotationDirection\n";
+    fg_dump += "    (0018,9305) FD 1                                        #   8, 1 RevolutionTime\n";
+    fg_dump += "    (0018,9306) FD 3                                        #   8, 1 SingleCollimationWidth\n";
+    fg_dump += "    (0018,9307) FD 2                                        #   8, 1 TotalCollimationWidth\n";
+    fg_dump += "    (0018,9378) US 1\\2\\3                                    #   6, 3 ReferencedPathIndex\n";
+    fg_dump += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    fg_dump += "  (fffe,e000) na (Item with explicit length #=8)          #   0, 1 Item\n";
+    fg_dump += "    (0018,0090) DS [12]                                     #   2, 1 DataCollectionDiameter\n";
+    fg_dump += "    (0018,1120) DS [11]                                     #   2, 1 GantryDetectorTilt\n";
+    fg_dump += "    (0018,1130) DS [10]                                     #   2, 1 TableHeight\n";
+    fg_dump += "    (0018,1140) CS [CW]                                     #   2, 1 RotationDirection\n";
+    fg_dump += "    (0018,9305) FD 7                                        #   8, 1 RevolutionTime\n";
+    fg_dump += "    (0018,9306) FD 8                                        #   8, 1 SingleCollimationWidth\n";
+    fg_dump += "    (0018,9307) FD 9                                        #   8, 1 TotalCollimationWidth\n";
+    fg_dump += "    (0018,9378) US 4\\5\\6                                    #   6, 3 ReferencedPathIndex\n";
+    fg_dump += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    fg_dump += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    fg_dump += "(fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+}
+
+static void check_ct_acquisition_details_fg(FGCTAcquisitionDetails& fg)
+{
+    OFCondition result;
+    OFString val;
+    OFVector<FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem*>& items = fg.getCTAcquisitionDetailsItems();
+    OFCHECK(items.size() == 2);
+    FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem* item1 = items[0];
+    OFVector<Uint16> vuint;
+    item1->getReferencedPathIndex(vuint);
+    OFCHECK(vuint.size() == 3);
+    OFCHECK((vuint[0] == 1) && (vuint[1] == 2) && (vuint[2] == 3));
+    Uint16 u16;
+    OFCHECK(item1->getReferencedPathIndex(u16, 0).good());
+    OFCHECK(u16 == 1);
+    OFCHECK(item1->getReferencedPathIndex(u16, 1).good());
+    OFCHECK(u16 == 2);
+    OFCHECK(item1->getReferencedPathIndex(u16, 2).good());
+    OFCHECK(u16 == 3);
+    FGCTAcquisitionDetails::E_RotationDirection rot;
+    OFCHECK(item1->getRotationDirection(rot).good());
+    OFCHECK(rot == FGCTAcquisitionDetails::E_RotationDirection_CC);
+    Float64 f64;
+    OFCHECK(item1->getRevolutionTime(f64).good());
+    OFCHECK(f64 == 1.0);
+    OFCHECK(item1->getTotalCollimationWidth(f64).good());
+    OFCHECK(f64 == 2.0);
+    OFCHECK(item1->getSingleCollimationWidth(f64).good());
+    OFCHECK(f64 == 3.0);
+    OFCHECK(item1->getTableHeight(f64).good());
+    OFCHECK(f64 == 4.0);
+    OFCHECK(item1->getGantryDetectorTilt(f64).good());
+    OFCHECK(f64 == 5.0);
+    OFCHECK(item1->getDataCollectionDiameter(f64).good());
+    OFCHECK(f64 == 6.0);
+
+    FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem* item2 = items[1];
+    vuint.clear();
+    item2->getReferencedPathIndex(vuint);
+    OFCHECK(vuint.size() == 3);
+    OFCHECK((vuint[0] == 4) && (vuint[1] == 5) && (vuint[2] == 6));
+    OFCHECK(item2->getReferencedPathIndex(u16, 0).good());
+    OFCHECK(u16 == 4);
+    OFCHECK(item2->getReferencedPathIndex(u16, 1).good());
+    OFCHECK(u16 == 5);
+    OFCHECK(item2->getReferencedPathIndex(u16, 2).good());
+    OFCHECK(u16 == 6);
+    OFCHECK(item2->getRotationDirection(rot).good());
+    OFCHECK(rot == FGCTAcquisitionDetails::E_RotationDirection_CW);
+    OFCHECK(item2->getRotationDirection(val).good());
+    OFCHECK(val == "CW");
+    OFCHECK(item2->getRevolutionTime(f64).good());
+    OFCHECK(f64 == 7.0);
+    OFCHECK(item2->getSingleCollimationWidth(f64).good());
+    OFCHECK(f64 == 8.0);
+    OFCHECK(item2->getTotalCollimationWidth(f64).good());
+    OFCHECK(f64 == 9.0);
+    OFCHECK(item2->getTableHeight(f64).good());
+    OFCHECK(f64 == 10.0);
+    OFCHECK(item2->getGantryDetectorTilt(f64).good());
+    OFCHECK(f64 == 11.0);
+    OFCHECK(item2->getDataCollectionDiameter(f64).good());
+    OFCHECK(f64 == 12.0);
+}
+
+OFTEST(dcmfg_ct_acquisition_details)
+{
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
+    OFString fg_dump;
+    init_template(fg_dump);
+
+    FGCTAcquisitionDetails fg;
+    FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem* fgi = new FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem;
+    OFVector<Uint16> vuint;
+    vuint.push_back(1);
+    vuint.push_back(2);
+    vuint.push_back(3);
+    OFCHECK(fgi->setReferencedPathIndex(vuint).good());
+    OFCHECK(fgi->setRotationDirection(FGCTAcquisitionDetails::E_RotationDirection_CC).good());
+    OFCHECK(fgi->setRevolutionTime(1.0).good());
+    OFCHECK(fgi->setTotalCollimationWidth(2.0).good());
+    OFCHECK(fgi->setSingleCollimationWidth(3.0).good());
+    OFCHECK(fgi->setTableHeight(4.0).good());
+    OFCHECK(fgi->setGantryDetectorTilt(5.0).good());
+    OFCHECK(fgi->setDataCollectionDiameter(6.0).good());
+    OFVector<FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem*>& items = fg.getCTAcquisitionDetailsItems();
+    items.push_back(fgi);
+
+    FGCTAcquisitionDetails::FGCTAcquisitionDetailsItem* fgi2 = fgi->clone();
+    vuint.clear();
+    vuint.push_back(4);
+    vuint.push_back(5);
+    vuint.push_back(6);
+    OFCHECK(fgi2->setReferencedPathIndex(vuint).good());
+    OFCHECK(fgi2->setRotationDirection(FGCTAcquisitionDetails::E_RotationDirection_CW).good());
+    OFCHECK(fgi2->setRevolutionTime(7.0).good());
+    OFCHECK(fgi2->setSingleCollimationWidth(8.0).good());
+    OFCHECK(fgi2->setTotalCollimationWidth(9.0).good());
+    OFCHECK(fgi2->setTableHeight(10.0).good());
+    OFCHECK(fgi2->setGantryDetectorTilt(11.0).good());
+    OFCHECK(fgi2->setDataCollectionDiameter(12.0).good());
+    items.push_back(fgi2);
+
+    // Check data structure in memory
+    check_ct_acquisition_details_fg(fg);
+
+    // Write to DcmItem and compare with pre-defined template
+    DcmItem dest_item;
+    OFCondition result = fg.write(dest_item);
+    OFCHECK(result.good());
+    OFStringStream out;
+    dest_item.print(out);
+    checkDump(out.str().c_str(), fg_dump);
+
+    // Test read method: Read from dataset, write again, and compare another time
+    FGCTAcquisitionDetails fg_for_read;
+    out.str(""); // set to empty
+    fg_for_read.read(dest_item);
+    dest_item.clear();
+    result = fg_for_read.write(dest_item);
+    OFCHECK(result.good());
+    dest_item.print(out);
+    checkDump(out.str().c_str(), fg_dump);
+
+    // Test compare() method
+    OFCHECK(fg.compare(fg_for_read) == 0);
+    OFCHECK(fgi->setTotalCollimationWidth(100.0).good());
+    OFCHECK(fg.compare(fg_for_read) != 0);
+
+    // Test clone() method
+    FGCTAcquisitionDetails* clone = OFstatic_cast(FGCTAcquisitionDetails*, fg.clone());
+    OFCHECK(clone != NULL);
+    OFCHECK(clone->compare(fg) == 0);
+    delete clone;
+}
+
+static void checkDump(const OFString& ds_dump, const OFString& expected_dump)
+{
+    OFBool dump_ok = (ds_dump == expected_dump);
+    OFCHECK(dump_ok);
+    if (!dump_ok)
+    {
+        CERR << "Dump produced: " << OFendl << ds_dump << OFendl;
+        CERR << "------------------------------------" << OFendl;
+        CERR << "Dump expected: " << OFendl << expected_dump << OFendl;
+        CERR << "------------------------------------" << OFendl;
+    }
+}
diff --git a/dcmfg/tests/t_ct_acquisition_type.cc b/dcmfg/tests/t_ct_acquisition_type.cc
new file mode 100644 (file)
index 0000000..0751b4d
--- /dev/null
@@ -0,0 +1,116 @@
+/*
+ *
+ *  Copyright (C) 2019-2020, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Tests for CT Acquisition Type FG class
+ *
+ */
+
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+
+#include "dcmtk/dcmfg/fgctacquisitiontype.h"
+#include "dcmtk/dcmfg/fginterface.h"
+#include "dcmtk/ofstd/ofcond.h"
+#include "dcmtk/ofstd/oftest.h"
+
+static void init_template(OFString& fg_dump)
+{
+    fg_dump += "(fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    fg_dump += "(0018,9301) SQ (Sequence with explicit length #=1)      #   0, 1 CTAcquisitionTypeSequence\n";
+    fg_dump += "  (fffe,e000) na (Item with explicit length #=4)          #   0, 1 Item\n";
+    fg_dump += "    (0018,9302) CS [STATIONARY]                             #  10, 1 AcquisitionType\n";
+    fg_dump += "    (0018,9303) FD 0.1234                                   #   8, 1 TubeAngle\n";
+    fg_dump += "    (0018,9333) CS [YES]                                    #   4, 1 ConstantVolumeFlag\n";
+    fg_dump += "    (0018,9334) CS [NO]                                     #   2, 1 FluoroscopyFlag\n";
+    fg_dump += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    fg_dump += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    fg_dump += "(fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+}
+
+static void check_ct_acquisition_type_fg(FGCTAcquisitionType& fg)
+{
+    OFCondition result;
+    OFString val;
+    OFCHECK(fg.getAcquisitionType(val).good());
+    OFCHECK(val == "STATIONARY");
+    Float64 f64;
+    OFCHECK(fg.getTubeAngle(f64).good());
+    OFCHECK(f64 == 0.1234);
+    OFCHECK(fg.getConstantVolumeFlag(val).good());
+    OFCHECK(val == "YES");
+    OFCHECK(fg.getFluoroscopyFlag(val).good());
+    OFCHECK(val == "NO");
+
+    // check enum getters()
+    FGCTAcquisitionType::E_ConstantVolumeFlag cv;
+    OFCHECK(fg.getConstantVolumeFlag(cv).good());
+    OFCHECK(cv == FGCTAcquisitionType::E_ConstVol_Yes);
+
+    FGCTAcquisitionType::E_FluoroscopyFlag fl;
+    OFCHECK(fg.getFluoroscopyFlag(fl).good());
+    OFCHECK(fl == FGCTAcquisitionType::E_Fluoroscopy_No);
+}
+
+OFTEST(dcmfg_ct_acquisition_type)
+{
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
+    OFString fg_dump;
+    init_template(fg_dump);
+
+    FGCTAcquisitionType fg;
+    OFCHECK(fg.setAcquisitionType(FGCTAcquisitionType::DT_AcquisitionType_Stationary).good());
+    OFCHECK(fg.setTubeAngle(0.1234).good());
+    OFCHECK(fg.setConstantVolumeFlag(FGCTAcquisitionType::E_ConstVol_Yes).good());
+    OFCHECK(fg.setFluoroscopyFlag(FGCTAcquisitionType::E_Fluoroscopy_No).good());
+
+    // Check data structure in memory
+    check_ct_acquisition_type_fg(fg);
+
+    // Write to DcmItem and compare with pre-defined template
+    DcmItem dest_item;
+    OFCondition result = fg.write(dest_item);
+    OFCHECK(result.good());
+    OFStringStream out;
+    dest_item.print(out);
+    OFCHECK(out.str() == fg_dump.c_str()); /**/
+
+    // Test read method: Read from dataset, write again, and compare another time
+    FGCTAcquisitionType fg_for_read;
+    out.str(""); // set to empty
+    fg_for_read.read(dest_item);
+    dest_item.clear();
+    result = fg_for_read.write(dest_item);
+    OFCHECK(result.good());
+    dest_item.print(out);
+    OFCHECK(out.str() == fg_dump.c_str());
+
+    // Test compare() method
+    OFCHECK(fg.compare(fg_for_read) == 0);
+    OFCHECK(fg_for_read.setAcquisitionType(FGCTAcquisitionType::DT_AcquisitionType_ConstantAngle).good());
+    OFCHECK(fg.compare(fg_for_read) != 0);
+
+    // Test clone() method
+    FGCTAcquisitionType* clone = OFstatic_cast(FGCTAcquisitionType*, fg.clone());
+    OFCHECK(clone != NULL);
+    OFCHECK(clone->compare(fg) == 0);
+    delete clone;
+}
diff --git a/dcmfg/tests/t_ct_image_frame_type.cc b/dcmfg/tests/t_ct_image_frame_type.cc
new file mode 100644 (file)
index 0000000..badef70
--- /dev/null
@@ -0,0 +1,115 @@
+/*
+ *
+ *  Copyright (C) 2019-2020, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Tests for CT Image Frame Type FG class
+ *
+ */
+
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+
+#include "dcmtk/dcmfg/fgctimageframetype.h"
+#include "dcmtk/dcmfg/fginterface.h"
+#include "dcmtk/ofstd/ofcond.h"
+#include "dcmtk/ofstd/oftest.h"
+
+static void init_template(OFString& fg_dump)
+{
+    fg_dump += "(fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    fg_dump += "(0018,9329) SQ (Sequence with explicit length #=1)      #   0, 1 CTImageFrameTypeSequence\n";
+    fg_dump += "  (fffe,e000) na (Item with explicit length #=4)          #   0, 1 Item\n";
+    fg_dump += "    (0008,9007) CS [ORIGINAL\\PRIMARY\\VOLUME\\NONE]           #  28, 4 FrameType\n";
+    fg_dump += "    (0008,9205) CS [MONOCHROME]                             #  10, 1 PixelPresentation\n";
+    fg_dump += "    (0008,9206) CS [VOLUME]                                 #   6, 1 VolumetricProperties\n";
+    fg_dump += "    (0008,9207) CS [VOLUME_RENDER]                          #  14, 1 VolumeBasedCalculationTechnique\n";
+    fg_dump += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    fg_dump += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    fg_dump += "(fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+}
+
+static void check_ct_image_frame_type_fg(FGCTImageFrameType& fg)
+{
+    OFCondition result;
+    OFString val;
+    OFCHECK(fg.getFrameType(val, -1 /* all components */).good());
+    OFCHECK(val == "ORIGINAL\\PRIMARY\\VOLUME\\NONE");
+    OFCHECK(fg.getPixelPresentation(val).good());
+    OFCHECK(val == "MONOCHROME");
+    OFCHECK(fg.getVolumetricProperties(val).good());
+    OFCHECK(val == "VOLUME");
+    OFCHECK(fg.getVolumeBasedCalculationTechnique(val).good());
+    OFCHECK(val == "VOLUME_RENDER");
+
+    // Check enum getters
+    FGCTImageFrameType::E_PixelPresentation pix;
+    OFCHECK(fg.getPixelPresentation(pix).good());
+    OFCHECK(pix == FGCTImageFrameType::E_PixelPres_Monochrome);
+
+    FGCTImageFrameType::E_VolumetricProperties vol;
+    OFCHECK(fg.getVolumetricProperties(vol).good());
+    OFCHECK(vol == FGCTImageFrameType::E_VolProp_Volume);
+}
+
+OFTEST(dcmfg_ct_image_frame_type)
+{
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
+    OFString fg_dump;
+    init_template(fg_dump);
+
+    FGCTImageFrameType fg;
+    OFCHECK(fg.setFrameType("ORIGINAL\\PRIMARY\\VOLUME\\NONE").good());
+    OFCHECK(fg.setPixelPresentation(FGCTImageFrameType::E_PixelPres_Monochrome).good());
+    OFCHECK(fg.setVolumetricProperties(FGCTImageFrameType::E_VolProp_Volume).good());
+    OFCHECK(fg.setVolumeBasedCalculationTechnique(FGCTImageFrameType::DT_VolBasedCalcTechnique_VolumeRender).good());
+
+    // Check data structure in memory
+    check_ct_image_frame_type_fg(fg);
+
+    // Write to DcmItem and compare with pre-defined template
+    DcmItem dest_item;
+    OFCondition result = fg.write(dest_item);
+    OFCHECK(result.good());
+    OFStringStream out;
+    dest_item.print(out);
+    OFCHECK(out.str() == fg_dump.c_str()); /**/
+
+    // Test read method: Read from dataset, write again, and compare another time
+    FGCTImageFrameType fg_for_read;
+    out.str(""); // set to empty
+    fg_for_read.read(dest_item);
+    dest_item.clear();
+    result = fg_for_read.write(dest_item);
+    OFCHECK(result.good());
+    dest_item.print(out);
+    OFCHECK(out.str() == fg_dump.c_str());
+
+    // Test compare() method
+    OFCHECK(fg.compare(fg_for_read) == 0);
+    OFCHECK(fg_for_read.setVolumetricProperties(FGCTImageFrameType::E_VolProp_Distorted).good());
+    OFCHECK(fg.compare(fg_for_read) != 0);
+
+    // Test clone() method
+    FGCTImageFrameType* clone = OFstatic_cast(FGCTImageFrameType*, fg.clone());
+    OFCHECK(clone != NULL);
+    OFCHECK(clone->compare(fg) == 0);
+    delete clone;
+}
diff --git a/dcmfg/tests/t_ct_position.cc b/dcmfg/tests/t_ct_position.cc
new file mode 100644 (file)
index 0000000..60a3346
--- /dev/null
@@ -0,0 +1,125 @@
+/*
+ *
+ *  Copyright (C) 2019-2020, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Tests for CT Position FG class
+ *
+ */
+
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+
+#include "dcmtk/dcmfg/fgctposition.h"
+#include "dcmtk/dcmfg/fginterface.h"
+#include "dcmtk/ofstd/ofcond.h"
+#include "dcmtk/ofstd/oftest.h"
+
+static void init_template(OFString& fg_dump)
+{
+    fg_dump += "(fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    fg_dump += "(0018,9326) SQ (Sequence with explicit length #=1)      #   0, 1 CTPositionSequence\n";
+    fg_dump += "  (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    fg_dump += "    (0018,9313) FD 1\\2\\3                                    #  24, 3 DataCollectionCenterPatient\n";
+    fg_dump
+        += "    (0018,9318) FD 4\\5\\6                                    #  24, 3 ReconstructionTargetCenterPatient\n";
+    fg_dump += "    (0018,9327) FD 1                                        #   8, 1 TablePosition\n";
+    fg_dump += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    fg_dump += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    fg_dump += "(fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+}
+
+static void check_ct_position_fg(FGCTPosition& fg)
+{
+    OFCondition result;
+    OFString val;
+    OFVector<Float64> vfl64;
+    Float64 fl64;
+    OFCHECK(fg.getTablePosition(fl64).good());
+    OFCHECK(fl64 == 1.0);
+    OFCHECK(fg.getDataCollectionCenterPatient(vfl64).good());
+    OFCHECK(vfl64.size() == 3);
+    OFCHECK(vfl64[0] == 1.0);
+    OFCHECK(vfl64[1] == 2.0);
+    OFCHECK(vfl64[2] == 3.0);
+    OFCHECK(fg.getDataCollectionCenterPatient(val, -1).good());
+    OFCHECK(val == "1\\2\\3");
+
+    vfl64.clear();
+    OFCHECK(fg.getReconstructionTargetCenterPatient(vfl64).good());
+    OFCHECK(vfl64.size() == 3);
+    OFCHECK(vfl64[0] == 4.0);
+    OFCHECK(vfl64[1] == 5.0);
+    OFCHECK(vfl64[2] == 6.0);
+    OFCHECK(fg.getReconstructionTargetCenterPatient(val, -1).good());
+    OFCHECK(val == "4\\5\\6");
+}
+
+OFTEST(dcmfg_ct_position)
+{
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
+    OFString fg_dump;
+    init_template(fg_dump);
+
+    FGCTPosition fg;
+    OFCHECK(fg.setTablePosition(1.0).good());
+    OFVector<Float64> vfl64;
+    vfl64.push_back(1.0);
+    vfl64.push_back(2.0);
+    vfl64.push_back(3.0);
+    OFCHECK(fg.setDataCollectionCenterPatient(vfl64).good());
+    vfl64.clear();
+    vfl64.push_back(4.0);
+    vfl64.push_back(5.0);
+    vfl64.push_back(6.0);
+    OFCHECK(fg.setReconstructionTargetCenterPatient(vfl64).good());
+
+    // Check data structure in memory
+    check_ct_position_fg(fg);
+
+    // Write to DcmItem and compare with pre-defined template
+    DcmItem dest_item;
+    OFCondition result = fg.write(dest_item);
+    OFCHECK(result.good());
+    OFStringStream out;
+    dest_item.print(out);
+    OFCHECK(out.str() == fg_dump.c_str()); /**/
+
+    // Test read method: Read from dataset, write again, and compare another time
+    FGCTPosition fg_for_read;
+    out.str(""); // set to empty
+    fg_for_read.read(dest_item);
+    dest_item.clear();
+    result = fg_for_read.write(dest_item);
+    OFCHECK(result.good());
+    dest_item.print(out);
+    OFCHECK(out.str() == fg_dump.c_str());
+
+    // Test compare() method
+    OFCHECK(fg.compare(fg_for_read) == 0);
+    OFCHECK(fg.setTablePosition(100.0).good());
+    OFCHECK(fg.compare(fg_for_read) != 0);
+
+    // Test clone() method
+    FGCTPosition* clone = OFstatic_cast(FGCTPosition*, fg.clone());
+    OFCHECK(clone != NULL);
+    OFCHECK(clone->compare(fg) == 0);
+    delete clone;
+}
diff --git a/dcmfg/tests/t_ct_table_dynamics.cc b/dcmfg/tests/t_ct_table_dynamics.cc
new file mode 100644 (file)
index 0000000..f4d9a2e
--- /dev/null
@@ -0,0 +1,136 @@
+/*
+ *
+ *  Copyright (C) 2019-2020, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Tests for CT Table Dynamics FG class
+ *
+ */
+
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+
+#include "dcmtk/dcmfg/fgcttabledynamics.h"
+#include "dcmtk/dcmfg/fginterface.h"
+#include "dcmtk/ofstd/ofcond.h"
+#include "dcmtk/ofstd/oftest.h"
+
+static void init_template(OFString& fg_dump)
+{
+    fg_dump += "(fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    fg_dump += "(0018,9308) SQ (Sequence with explicit length #=2)      #   0, 1 CTTableDynamicsSequence\n";
+    fg_dump += "  (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    fg_dump += "    (0018,9309) FD 1                                        #   8, 1 TableSpeed\n";
+    fg_dump += "    (0018,9310) FD 2                                        #   8, 1 TableFeedPerRotation\n";
+    fg_dump += "    (0018,9311) FD 3                                        #   8, 1 SpiralPitchFactor\n";
+    fg_dump += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    fg_dump += "  (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    fg_dump += "    (0018,9309) FD 4                                        #   8, 1 TableSpeed\n";
+    fg_dump += "    (0018,9310) FD 5                                        #   8, 1 TableFeedPerRotation\n";
+    fg_dump += "    (0018,9311) FD 6                                        #   8, 1 SpiralPitchFactor\n";
+    fg_dump += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    fg_dump += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    fg_dump += "(fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+}
+
+static void check_ct_table_dynamics_fg(FGCTTableDynamics& fg)
+{
+    OFCondition result;
+    OFString val;
+    Float64 fl64;
+    OFVector<FGCTTableDynamics::FGCTTableDynamicsItem*>::iterator item = fg.getCTTableDynamicsItems().begin();
+    OFCHECK((*item)->getTableSpeed(fl64).good());
+    OFCHECK(fl64 == 1.0);
+    OFCHECK((*item)->getTableSpeed(val).good());
+    OFCHECK(val == "1");
+    OFCHECK((*item)->getTableFeedPerRotation(fl64).good());
+    OFCHECK(fl64 == 2.0);
+    OFCHECK((*item)->getTableFeedPerRotation(val).good());
+    OFCHECK(val == "2");
+    OFCHECK((*item)->getSpiralPitchFactor(fl64).good());
+    OFCHECK(fl64 == 3.0);
+    OFCHECK((*item)->getSpiralPitchFactor(val).good());
+    OFCHECK(val == "3");
+
+    item++;
+    OFCHECK((*item)->getTableSpeed(fl64).good());
+    OFCHECK(fl64 == 4.0);
+    OFCHECK((*item)->getTableSpeed(val).good());
+    OFCHECK(val == "4");
+    OFCHECK((*item)->getTableFeedPerRotation(fl64).good());
+    OFCHECK(fl64 == 5.0);
+    OFCHECK((*item)->getTableFeedPerRotation(val).good());
+    OFCHECK(val == "5");
+    OFCHECK((*item)->getSpiralPitchFactor(fl64).good());
+    OFCHECK(fl64 == 6.0);
+    OFCHECK((*item)->getSpiralPitchFactor(val).good());
+    OFCHECK(val == "6");
+}
+
+OFTEST(dcmfg_ct_table_dynamics)
+{
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
+    OFString fg_dump;
+    init_template(fg_dump);
+
+    FGCTTableDynamics fg;
+    FGCTTableDynamics::FGCTTableDynamicsItem* fgi1 = new FGCTTableDynamics::FGCTTableDynamicsItem;
+    OFCHECK(fgi1->setTableSpeed(1.0).good());
+    OFCHECK(fgi1->setTableFeedPerRotation(2.0).good());
+    OFCHECK(fgi1->setSpiralPitchFactor(3.0).good());
+    FGCTTableDynamics::FGCTTableDynamicsItem* fgi2 = new FGCTTableDynamics::FGCTTableDynamicsItem;
+    OFCHECK(fgi2->setTableSpeed(4.0).good());
+    OFCHECK(fgi2->setTableFeedPerRotation(5.0).good());
+    OFCHECK(fgi2->setSpiralPitchFactor(6.0).good());
+    fg.getCTTableDynamicsItems().push_back(fgi1);
+    fg.getCTTableDynamicsItems().push_back(fgi2);
+
+    // Check data structure in memory
+    check_ct_table_dynamics_fg(fg);
+
+    // Write to DcmItem and compare with pre-defined template
+    DcmItem dest_item;
+    OFCondition result = fg.write(dest_item);
+    OFCHECK(result.good());
+    OFStringStream out;
+    dest_item.print(out);
+    OFCHECK(out.str() == fg_dump.c_str()); /**/
+
+    // Test read method: Read from dataset, write again, and compare another time
+    FGCTTableDynamics fg_for_read;
+    out.str(""); // set to empty
+    fg_for_read.read(dest_item);
+    dest_item.clear();
+    result = fg_for_read.write(dest_item);
+    OFCHECK(result.good());
+    dest_item.print(out);
+    OFCHECK(out.str() == fg_dump.c_str());
+
+    // Test compare() method
+    OFCHECK(fg.compare(fg_for_read) == 0);
+    OFCHECK(fgi2->setTableSpeed(100.0).good());
+    OFCHECK(fg.compare(fg_for_read) != 0);
+
+    // Test clone() method
+    FGCTTableDynamics* clone = OFstatic_cast(FGCTTableDynamics*, fg.clone());
+    OFCHECK(clone != NULL);
+    OFCHECK(clone->compare(fg) == 0);
+    delete clone;
+}
index f3147502946dfdc28167f7b0ef19bae0bf960cd5..a3384c1250b4d752caa1905fc15ad8fa48a4a9b4 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2019, OFFIS e.V.
+ *  Copyright (C) 2019-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -63,10 +63,12 @@ static void check_deriv_image_fg(FGDerivationImage& fg)
 {
     OFVector<DerivationImageItem*> deriv_img_items = fg.getDerivationImageItems();
     OFCHECK(deriv_img_items.size() == 1);
-    if (deriv_img_items.size() == 0) return;
+    if (deriv_img_items.size() == 0)
+        return;
     OFVector<CodeSequenceMacro*>& deriv_code_items = deriv_img_items[0]->getDerivationCodeItems();
     OFCHECK(deriv_code_items.size() == 1);
-    if (deriv_code_items.size() == 0) return;
+    if (deriv_code_items.size() == 0)
+        return;
     CodeSequenceMacro* code_item = deriv_code_items[0];
     OFString str;
     code_item->getCodeValue(str);
@@ -103,6 +105,13 @@ static void check_deriv_image_fg(FGDerivationImage& fg)
 
 OFTEST(dcmfg_derivation_image)
 {
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
     OFString fg_dump;
     init_template(fg_dump);
 
@@ -112,11 +121,13 @@ OFTEST(dcmfg_derivation_image)
     OFCondition result              = fg.addDerivationImageItem(deriv_code, "Some Description", deriv_item);
     OFCHECK(result.good());
     OFCHECK(deriv_item != NULL);
-    if (result.bad() || !deriv_item) return;
+    if (result.bad() || !deriv_item)
+        return;
 
     SourceImageItem* src_image_item = new SourceImageItem();
     OFCHECK(src_image_item != NULL);
-    if (!deriv_item) return;
+    if (!deriv_item)
+        return;
     OFCHECK(src_image_item->getImageSOPInstanceReference().addReferencedFrameNumber(1).good());
     OFCHECK(src_image_item->getImageSOPInstanceReference().addReferencedFrameNumber(2).good());
     OFCHECK(src_image_item->getImageSOPInstanceReference().addReferencedSegmentNumber(3).good());
@@ -146,7 +157,8 @@ OFTEST(dcmfg_derivation_image)
     dest_item.clear();
     result = fg_for_read.write(dest_item);
     OFCHECK(result.good());
-    if (result.bad()) return;
+    if (result.bad())
+        return;
     dest_item.print(out);
     OFCHECK(out.str() == fg_dump.c_str());
 
@@ -158,7 +170,8 @@ OFTEST(dcmfg_derivation_image)
     // Test clone() method
     FGDerivationImage* clone = OFstatic_cast(FGDerivationImage*, fg.clone());
     OFCHECK(clone != NULL);
-    if (clone == NULL) return;
+    if (clone == NULL)
+        return;
     OFCHECK(clone->compare(fg) == 0);
     delete clone;
 }
index ebd87093e8c047bf0b7646eed3c6004f635cead4..4a92feec58ba02a77a315f8d3da182326548454c 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2019, OFFIS e.V.
+ *  Copyright (C) 2019-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -84,6 +84,13 @@ static void check_frame_content_fg(FGFrameContent& fg)
 
 OFTEST(dcmfg_frame_content)
 {
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
     OFString fg_dump;
     init_template(fg_dump);
 
@@ -119,7 +126,8 @@ OFTEST(dcmfg_frame_content)
     dest_item.clear();
     result = fg_for_read.write(dest_item);
     OFCHECK(result.good());
-    if (result.bad()) return;
+    if (result.bad())
+        return;
     dest_item.print(out);
     OFCHECK(out.str() == fg_dump.c_str());
 
@@ -131,7 +139,8 @@ OFTEST(dcmfg_frame_content)
     // Test clone() method
     FGFrameContent* clone = OFstatic_cast(FGFrameContent*, fg.clone());
     OFCHECK(clone != NULL);
-    if (clone == NULL) return;
+    if (clone == NULL)
+        return;
     OFCHECK(clone->compare(fg) == 0);
     delete clone;
 }
diff --git a/dcmfg/tests/t_irradiation_event_identification.cc b/dcmfg/tests/t_irradiation_event_identification.cc
new file mode 100644 (file)
index 0000000..54df4de
--- /dev/null
@@ -0,0 +1,95 @@
+/*
+ *
+ *  Copyright (C) 2019-2020, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmfg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Tests for Irradiation Event Identification FG class
+ *
+ */
+
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+
+#include "dcmtk/dcmfg/fginterface.h"
+#include "dcmtk/dcmfg/fgirradiationeventid.h"
+#include "dcmtk/ofstd/ofcond.h"
+#include "dcmtk/ofstd/oftest.h"
+
+static void init_template(OFString& fg_dump)
+{
+    fg_dump += "(fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    fg_dump
+        += "(0018,9477) SQ (Sequence with explicit length #=1)      #   0, 1 IrradiationEventIdentificationSequence\n";
+    fg_dump += "  (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    fg_dump += "    (0008,3010) UI [1.2.3.4]                                #   8, 1 IrradiationEventUID\n";
+    fg_dump += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    fg_dump += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    fg_dump += "(fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+}
+
+static void check_irradiation_event_identification_fg(FGIrradiationEventIdentification& fg)
+{
+    OFCondition result;
+    OFString val;
+    OFCHECK(fg.getIrradiationEventUID(val).good());
+    OFCHECK(val == "1.2.3.4");
+}
+
+OFTEST(dcmfg_irradiation_event_identification)
+{
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
+    OFString fg_dump;
+    init_template(fg_dump);
+
+    FGIrradiationEventIdentification fg;
+    OFCHECK(fg.setIrradiationEventUID("1.2.3.4").good());
+
+    // Check data structure in memory
+    check_irradiation_event_identification_fg(fg);
+
+    // Write to DcmItem and compare with pre-defined template
+    DcmItem dest_item;
+    OFCondition result = fg.write(dest_item);
+    OFCHECK(result.good());
+    OFStringStream out;
+    dest_item.print(out);
+    OFCHECK(out.str() == fg_dump.c_str()); /**/
+
+    // Test read method: Read from dataset, write again, and compare another time
+    FGIrradiationEventIdentification fg_for_read;
+    out.str(""); // set to empty
+    fg_for_read.read(dest_item);
+    dest_item.clear();
+    result = fg_for_read.write(dest_item);
+    OFCHECK(result.good());
+    dest_item.print(out);
+    OFCHECK(out.str() == fg_dump.c_str());
+
+    // Test compare() method
+    OFCHECK(fg.compare(fg_for_read) == 0);
+    fg_for_read.setIrradiationEventUID("5.6.7.8");
+    OFCHECK(fg.compare(fg_for_read) != 0);
+
+    // Test clone() method
+    FGIrradiationEventIdentification* clone = OFstatic_cast(FGIrradiationEventIdentification*, fg.clone());
+    OFCHECK(clone != NULL);
+    OFCHECK(clone->compare(fg) == 0);
+    delete clone;
+}
index af66e545d4783a286d960e523191c69dfbc8d9dc..30ac798ccb40e7e3f50d4cbceb8b5c87d4d891e9 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015, OFFIS e.V.
+ *  Copyright (C) 2015-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
  */
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/ofstd/oftest.h"
 
+OFTEST_REGISTER(dcmfg_concatenation_creator);
+OFTEST_REGISTER(dcmfg_concatenation_creator_fail);
+OFTEST_REGISTER(dcmfg_concatenation_loader);
+
+OFTEST_REGISTER(dcmfg_ct_image_frame_type);
+OFTEST_REGISTER(dcmfg_ct_acquisition_type);
+OFTEST_REGISTER(dcmfg_ct_acquisition_details);
+OFTEST_REGISTER(dcmfg_ct_table_dynamics);
+OFTEST_REGISTER(dcmfg_ct_position);
 OFTEST_REGISTER(dcmfg_derivation_image);
 OFTEST_REGISTER(dcmfg_frame_content);
+OFTEST_REGISTER(dcmfg_irradiation_event_identification);
+
 OFTEST_MAIN("dcmfg")
index 4fa8482ce93443eca663b170765ce180ade349c2..b694e5901924eeb743cdfad47343f6650535d437 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1996-2018, OFFIS e.V.
+ *  Copyright (C) 1996-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -132,7 +132,7 @@ int main(int argc, char *argv[])
     OFCmdUnsignedInt    opt_frameCount = 1;               /* default: one frame */
     OFBool              opt_useFrameNumber = OFFalse;     /* default: use frame counter */
     OFBool              opt_multiFrame = OFFalse;         /* default: no multiframes */
-    int                 opt_convertToGrayscale = 0;       /* default: color or grayscale */
+    int                 opt_convertToGrayscale = 0;       /* default: no conversion */
     int                 opt_changePolarity = 0;           /* default: normal polarity */
     int                 opt_useAspectRatio = 1;           /* default: use aspect ratio for scaling */
     OFCmdUnsignedInt    opt_useInterpolation = 1;         /* default: use interpolation method '1' for scaling */
@@ -233,7 +233,7 @@ int main(int argc, char *argv[])
 
      cmd.addSubGroup("frame selection:");
       cmd.addOption("--frame",              "+F",   1, "[n]umber: integer",
-                                                        "select specified frame (default: 1)");
+                                                       "select specified frame (default: 1)");
       cmd.addOption("--frame-range",        "+Fr",  2, "[n]umber [c]ount: integer",
                                                        "select c frames beginning with frame n");
       cmd.addOption("--all-frames",         "+Fa",     "select all frames");
@@ -249,7 +249,7 @@ int main(int argc, char *argv[])
       cmd.addOption("--flip-both-axes",     "+Lhv",    "flip image horizontally and vertically");
 
      cmd.addSubGroup("scaling:");
-      cmd.addOption("--recognize-aspect",   "+a",      "recognize pixel aspect ratio (default)");
+      cmd.addOption("--recognize-aspect",   "+a",      "recognize pixel aspect ratio when scaling (def.)");
       cmd.addOption("--ignore-aspect",      "-a",      "ignore pixel aspect ratio when scaling");
       cmd.addOption("--interpolate",        "+i",   1, "[n]umber of algorithm: integer",
                                                        "use interpolation when scaling (1..4, def: 1)");
@@ -371,7 +371,7 @@ int main(int argc, char *argv[])
 #endif
 
      cmd.addSubGroup("other transformations:");
-      cmd.addOption("--grayscale",          "+G",      "convert to grayscale if necessary");
+      cmd.addOption("--grayscale",          "+G",      "convert color image to grayscale (monochrome)");
       cmd.addOption("--change-polarity",    "+P",      "change polarity (invert pixel output)");
       cmd.addOption("--clip-region",        "+C",   4, "[l]eft [t]op [w]idth [h]eight: integer",
                                                        "clip image region (l, t, w, h)");
@@ -1101,7 +1101,7 @@ int main(int argc, char *argv[])
             return 1;
         }
 
-        /* convert to grayscale if necessary */
+        /* convert to grayscale if image is not monochrome */
         if ((opt_convertToGrayscale) && (!di->isMonochrome()))
         {
              OFLOG_INFO(dcm2pnmLogger, "converting image to grayscale");
index 6cd1d31a1f5575b310165c4634982a0fd2dfb7db..557a62e1ee690ea3d9050ac84a91925bb453349c 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2001-2018, OFFIS e.V.
+ *  Copyright (C) 2001-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -72,7 +72,7 @@ int main(int argc, char *argv[])
     OFCommandLine cmd;
 
     E_FileReadMode opt_readMode = ERM_autoDetect;
-    E_FileWriteMode opt_writeMode = EWM_fileformat;
+    E_FileWriteMode opt_writeMode = EWM_createNewMeta;
     E_TransferSyntax opt_ixfer = EXS_Unknown;
     E_TransferSyntax opt_oxfer = EXS_Unknown;
     E_GrpLenEncoding opt_oglenc = EGL_recalcGL;
@@ -328,7 +328,7 @@ int main(int argc, char *argv[])
       cmd.endOptionBlock();
 
       cmd.beginOptionBlock();
-      if (cmd.findOption("--write-file")) opt_writeMode = EWM_fileformat;
+      if (cmd.findOption("--write-file")) opt_writeMode = EWM_createNewMeta;
       if (cmd.findOption("--write-dataset")) opt_writeMode = EWM_dataset;
       cmd.endOptionBlock();
 
@@ -486,7 +486,7 @@ int main(int argc, char *argv[])
     OFLOG_INFO(dcmquantLogger, "write converted DICOM file");
 
     // update file meta information with new SOP Instance UID
-    if ((opt_uidcreation || opt_secondarycapture) && (opt_writeMode == EWM_fileformat))
+    if ((opt_uidcreation || opt_secondarycapture) && (opt_writeMode == EWM_createNewMeta))
         opt_writeMode = EWM_updateMeta;
 
     error = fileformat.saveFile(opt_ofname, opt_oxfer, opt_oenctype, opt_oglenc, opt_opadenc,
index 7cadfce7269b1c753423eabc02e8d8c6fda019a8..e762d6e1f90d4219230603432ab414389df269c9 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2002-2018, OFFIS e.V.
+ *  Copyright (C) 2002-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -74,7 +74,7 @@ int main(int argc, char *argv[])
 
     OFBool opt_uidCreation = OFTrue;
     E_FileReadMode opt_readMode = ERM_autoDetect;
-    E_FileWriteMode opt_writeMode = EWM_fileformat;
+    E_FileWriteMode opt_writeMode = EWM_createNewMeta;
     E_TransferSyntax opt_ixfer = EXS_Unknown;
     E_TransferSyntax opt_oxfer = EXS_Unknown;
     E_GrpLenEncoding opt_oglenc = EGL_recalcGL;
@@ -140,7 +140,7 @@ int main(int argc, char *argv[])
       cmd.addOption("--conv-never",         "+cn",      "never convert color space");
 #endif
      cmd.addSubGroup("scaling:");
-      cmd.addOption("--recognize-aspect",    "+a",      "recognize pixel aspect ratio (default)");
+      cmd.addOption("--recognize-aspect",    "+a",      "recognize pixel aspect ratio when scaling (def)");
       cmd.addOption("--ignore-aspect",       "-a",      "ignore pixel aspect ratio when scaling");
       cmd.addOption("--interpolate",         "+i",   1, "[n]umber of algorithm: integer",
                                                         "use interpolation when scaling (1..4, def: 1)");
@@ -330,7 +330,7 @@ int main(int argc, char *argv[])
       /* output options */
 
       cmd.beginOptionBlock();
-      if (cmd.findOption("--write-file")) opt_writeMode = EWM_fileformat;
+      if (cmd.findOption("--write-file")) opt_writeMode = EWM_createNewMeta;
       if (cmd.findOption("--write-dataset")) opt_writeMode = EWM_dataset;
       cmd.endOptionBlock();
 
@@ -567,7 +567,7 @@ int main(int argc, char *argv[])
     if (!derivationDescription.empty())
     {
         const char *oldDerivation = NULL;
-        if (dataset->findAndGetString(DCM_DerivationDescription, oldDerivation).good())
+        if (dataset->findAndGetString(DCM_DerivationDescription, oldDerivation).good() && oldDerivation)
         {
              // append old Derivation Description, if any
             derivationDescription += " [";
@@ -618,9 +618,6 @@ int main(int argc, char *argv[])
         // create new SOP instance UID
         char new_uid[100];
         dataset->putAndInsertString(DCM_SOPInstanceUID, dcmGenerateUniqueIdentifier(new_uid));
-        // force meta-header to refresh SOP Instance UID
-        if (opt_writeMode == EWM_fileformat)
-            opt_writeMode = EWM_updateMeta;
     }
 
     // ======================================================================
index cbd485766a10364e370a355fa184acac98d0eff7..25e22079e1934d30d55f73ccf8ad147d463c1d14 100644 (file)
@@ -128,7 +128,7 @@ flipping:
 scaling:
 
   +a    --recognize-aspect
-          recognize pixel aspect ratio (default)
+          recognize pixel aspect ratio when scaling (default)
 
   -a    --ignore-aspect
           ignore pixel aspect ratio when scaling
@@ -329,7 +329,7 @@ PNG format:
 other transformations:
 
   +G    --grayscale
-          convert to grayscale if necessary
+          convert color image to grayscale (monochrome)
 
   +P    --change-polarity
           change polarity (invert pixel output)
@@ -497,6 +497,6 @@ It is an error if no data dictionary can be loaded.
 
 \section dcm2pnm_copyright COPYRIGHT
 
-Copyright (C) 1998-2014 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 1998-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index bec7e6dacee9a0b77c4bc61347b661d8d5b738f0..bfad04d3afb60dd47fe35eeda09e34a5759a2832 100644 (file)
@@ -92,7 +92,7 @@ input transfer syntax:
 scaling:
 
   +a    --recognize-aspect
-          recognize pixel aspect ratio (default)
+          recognize pixel aspect ratio when scaling (default)
 
   -a    --ignore-aspect
           ignore pixel aspect ratio when scaling
@@ -266,6 +266,6 @@ It is an error if no data dictionary can be loaded.
 
 \section dcmscale_copyright COPYRIGHT
 
-Copyright (C) 2002-2014 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 2002-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index 715ee833eda0ba7322a1ccea0f2a194891f1a3f6..89a965a3354e6a06fe19e329a17e58cfd2eb4904 100644 (file)
@@ -69,7 +69,7 @@ public:
 
   /** adds all pixels of all frames of the given image (which must be a
    *  color image) to the hash table.  The counter (integer value associated
-   *  to each color) counts the occurence of the color in the image.
+   *  to each color) counts the occurrence of the color in the image.
    *  If more than maxcolors colors are found, the function returns zero.
    *  @param image image in which colors are to be counted
    *  @param newmaxval maximum pixel value to which the contents of the
index 066e0a9ec90eb77b4e4db73bee2c7e7cb5bfb3ab..2bec9944f7506063a9f056a6065ff03a409ca19d 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2001-2010, OFFIS e.V.
+ *  Copyright (C) 2001-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -27,6 +27,7 @@
 #include "dcmtk/dcmdata/dctypes.h"
 #include "dcmtk/dcmimgle/diimage.h"
 #include "dcmtk/dcmimage/dipitiff.h"
+#include "dcmtk/dcmdata/dcuid.h"      /* for dcmtk version */
 
 BEGIN_EXTERN_C
 #include <tiffio.h>
@@ -145,7 +146,8 @@ int DiTIFFPlugin::write(
           TIFFSetField(tif, TIFFTAG_PHOTOMETRIC, photometric);
           TIFFSetField(tif, TIFFTAG_FILLORDER, FILLORDER_MSB2LSB);
           TIFFSetField(tif, TIFFTAG_DOCUMENTNAME, "unnamed");
-          TIFFSetField(tif, TIFFTAG_IMAGEDESCRIPTION, "converted DICOM image");
+          TIFFSetField(tif, TIFFTAG_IMAGEDESCRIPTION, "Converted DICOM Image");
+          TIFFSetField(tif, TIFFTAG_SOFTWARE, "OFFIS DCMTK " OFFIS_DCMTK_VERSION);
           TIFFSetField(tif, TIFFTAG_SAMPLESPERPIXEL, samplesperpixel);
           TIFFSetField(tif, TIFFTAG_ROWSPERSTRIP, opt_rowsperstrip);
           /* TIFFSetField(tif, TIFFTAG_STRIPBYTECOUNTS, rows / opt_rowsperstrip); */
index e5d11b788c2b405a7e65bf8688a82a07e9ebb4d0..9c49925ba56f23e22ac63fafc37da8bb0152c960 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1996-2018, OFFIS e.V.
+ *  Copyright (C) 1996-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -350,7 +350,8 @@ class DiMonoOutputPixelTemplate
                 DCMIMGLE_DEBUG("applying VOI transformation with LUT (" << vlut->getCount() << " entries)");
                 const DiDisplayLUT *dlut = NULL;
                 const double minvalue = vlut->getMinValue();
-                const double outrange = OFstatic_cast(double, high) - OFstatic_cast(double, low) + 1;
+                const double lowvalue = OFstatic_cast(double, low);
+                const double outrange = OFstatic_cast(double, high) - lowvalue + 1;
                 unsigned long i;
                 if (minvalue == vlut->getMaxValue())                                    // LUT has only one entry or all entries are equal
                 {
@@ -369,7 +370,7 @@ class DiMonoOutputPixelTemplate
                                 value = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, plut->getValue(value2))));
                         } else {                                                        // don't use display: invalid or absent
                             DCMIMGLE_TRACE("monochrome rendering: VOI LUT #2");
-                            value = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value2)) * outrange / OFstatic_cast(double, plut->getAbsMaxRange()));
+                            value = OFstatic_cast(T3, lowvalue + OFstatic_cast(double, plut->getValue(value2)) * outrange / OFstatic_cast(double, plut->getAbsMaxRange()));
                         }
                     } else {                                                            // has no presentation LUT
                         createDisplayLUT(dlut, disp, vlut->getBits());
@@ -382,7 +383,7 @@ class DiMonoOutputPixelTemplate
                                 value = OFstatic_cast(T3, dlut->getValue(OFstatic_cast(Uint16, minvalue)));
                         } else {                                                        // don't use display: invalid or absent
                             DCMIMGLE_TRACE("monochrome rendering: VOI LUT #4");
-                            value = OFstatic_cast(T3, OFstatic_cast(double, low) + (minvalue / OFstatic_cast(double, vlut->getAbsMaxRange())) * outrange);
+                            value = OFstatic_cast(T3, lowvalue + (minvalue / OFstatic_cast(double, vlut->getAbsMaxRange())) * outrange);
                         }
                     }
                     OFBitmanipTemplate<T3>::setMem(Data, value, Count);                 // set output pixels to LUT value
@@ -449,7 +450,7 @@ class DiMonoOutputPixelTemplate
                                         value2 = lastvalue;
                                     else
                                         value2 = OFstatic_cast(Uint32, OFstatic_cast(double, vlut->getValue(value)) * gradient1);
-                                    *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value2)) * gradient2);
+                                    *(q++) = OFstatic_cast(T3, lowvalue + OFstatic_cast(double, plut->getValue(value2)) * gradient2);
                                 }
                             }
                             const T3 *lut0 = lut - OFstatic_cast(T2, inter->getAbsMinimum());  // points to 'zero' entry
@@ -501,15 +502,15 @@ class DiMonoOutputPixelTemplate
                                         value2 = lastvalue;
                                     else
                                         value2 = OFstatic_cast(Uint32, OFstatic_cast(double, vlut->getValue(value)) * gradient1);
-                                    *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value2)) * gradient2);
+                                    *(q++) = OFstatic_cast(T3, lowvalue + OFstatic_cast(double, plut->getValue(value2)) * gradient2);
                                 }
                             }
                         }
                     } else {                                                              // has no presentation LUT
                         createDisplayLUT(dlut, disp, vlut->getBits());
                         const double gradient = outrange / OFstatic_cast(double, vlut->getAbsMaxRange());
-                        const T3 firstvalue = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, vlut->getFirstValue()) * gradient);
-                        const T3 lastvalue = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, vlut->getLastValue()) * gradient);
+                        const T3 firstvalue = OFstatic_cast(T3, lowvalue + OFstatic_cast(double, vlut->getFirstValue()) * gradient);
+                        const T3 lastvalue = OFstatic_cast(T3, lowvalue + OFstatic_cast(double, vlut->getLastValue()) * gradient);
                         if (initOptimizationLUT(lut, ocnt))
                         {                                                                 // use LUT for optimization
                             q = lut;
@@ -549,7 +550,7 @@ class DiMonoOutputPixelTemplate
                                     else if (value >= lastentry)
                                         *(q++) = lastvalue;
                                     else
-                                        *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, vlut->getValue(value)) * gradient);
+                                        *(q++) = OFstatic_cast(T3, lowvalue + OFstatic_cast(double, vlut->getValue(value)) * gradient);
                                 }
                             }
                             const T3 *lut0 = lut - OFstatic_cast(T2, inter->getAbsMinimum());   // points to 'zero' entry
@@ -595,7 +596,7 @@ class DiMonoOutputPixelTemplate
                                     else if (value >= lastentry)
                                         *(q++) = lastvalue;
                                     else
-                                        *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, vlut->getValue(value)) * gradient);
+                                        *(q++) = OFstatic_cast(T3, lowvalue + OFstatic_cast(double, vlut->getValue(value)) * gradient);
                                 }
                             }
                         }
@@ -636,7 +637,8 @@ class DiMonoOutputPixelTemplate
                 DCMIMGLE_DEBUG("applying no VOI transformation (linear scaling)");
                 const double absmin = inter->getAbsMinimum();
                 const double absmax = inter->getAbsMaximum();
-                const double outrange = OFstatic_cast(double, high) - OFstatic_cast(double, low) + 1;  // output range
+                const double lowvalue = OFstatic_cast(double, low);
+                const double outrange = OFstatic_cast(double, high) - lowvalue + 1;   // output range
                 const unsigned long ocnt = determineOptimizationCount(inter->getAbsMaxRange());        // number of LUT entries
                 DCMIMGLE_TRACE("intermediate pixel data - absmin: " << absmin << ", absmax: " << absmax);
                 const T1 *p = pixel + start;
@@ -676,7 +678,7 @@ class DiMonoOutputPixelTemplate
                             for (i = 0; i < ocnt; ++i)
                             {
                                 value = OFstatic_cast(Uint32, OFstatic_cast(double, i) * gradient1);
-                                *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value)) * gradient2);
+                                *(q++) = OFstatic_cast(T3, lowvalue + OFstatic_cast(double, plut->getValue(value)) * gradient2);
                             }
                         }
                         const T3 *lut0 = lut - OFstatic_cast(T2, inter->getAbsMinimum());  // points to 'zero' entry
@@ -709,7 +711,7 @@ class DiMonoOutputPixelTemplate
                             for (i = Count; i != 0; --i)
                             {
                                 value = OFstatic_cast(Uint32, (OFstatic_cast(double, *(p++)) - absmin) * gradient1);
-                                *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value)) * gradient2);
+                                *(q++) = OFstatic_cast(T3, lowvalue + OFstatic_cast(double, plut->getValue(value)) * gradient2);
                             }
                         }
                     }
@@ -733,7 +735,7 @@ class DiMonoOutputPixelTemplate
                         } else {                                                      // don't use display: invalid or absent
                             DCMIMGLE_TRACE("monochrome rendering: VOI NONE #6");
                             for (i = 0; i < ocnt; ++i)                                // calculating LUT entries
-                                *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, i) * gradient);
+                                *(q++) = OFstatic_cast(T3, lowvalue + OFstatic_cast(double, i) * gradient);
                         }
                         const T3 *lut0 = lut - OFstatic_cast(T2, inter->getAbsMinimum());  // points to 'zero' entry
                         q = Data;
@@ -756,7 +758,7 @@ class DiMonoOutputPixelTemplate
                         } else {                                                      // don't use display: invalid or absent
                             DCMIMGLE_TRACE("monochrome rendering: VOI NONE #8");
                             for (i = Count; i != 0; --i)
-                                *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + (OFstatic_cast(double, *(p++)) - absmin) * gradient);
+                                *(q++) = OFstatic_cast(T3, lowvalue + (OFstatic_cast(double, *(p++)) - absmin) * gradient);
                         }
                     }
                 }
@@ -798,7 +800,8 @@ class DiMonoOutputPixelTemplate
                 DCMIMGLE_DEBUG("applying sigmoid VOI transformation with window center = " << center << ", width = " << width);
                 const DiDisplayLUT *dlut = NULL;
                 const double absmin = inter->getAbsMinimum();
-                const double outrange = OFstatic_cast(double, high) - OFstatic_cast(double, low);  // output range
+                const double lowvalue = OFstatic_cast(double, low);
+                const double outrange = OFstatic_cast(double, high) - lowvalue;       // output range
                 const unsigned long ocnt = determineOptimizationCount(inter->getAbsMaxRange());    // number of LUT entries
                 const T1 *p = pixel + start;
                 T3 *q = Data;
@@ -834,7 +837,7 @@ class DiMonoOutputPixelTemplate
                             {
                                 value = OFstatic_cast(double, i) + absmin;
                                 value2 = OFstatic_cast(Uint32, plutcnt_1 / (1 + exp(-4 * (value - center) / width)));
-                                *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value2)) * gradient);
+                                *(q++) = OFstatic_cast(T3, lowvalue + OFstatic_cast(double, plut->getValue(value2)) * gradient);
                             }
                         }
                         const T3 *lut0 = lut - OFstatic_cast(T2, absmin);             // points to 'zero' entry
@@ -863,7 +866,7 @@ class DiMonoOutputPixelTemplate
                             {
                                 value = OFstatic_cast(double, *(p++));
                                 value2 = OFstatic_cast(Uint32, plutcnt_1 / (1 + exp(-4 * (value - center) / width)));
-                                *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value2)) * gradient);
+                                *(q++) = OFstatic_cast(T3, lowvalue + OFstatic_cast(double, plut->getValue(value2)) * gradient);
                             }
                         }
                     }
@@ -888,7 +891,7 @@ class DiMonoOutputPixelTemplate
                             for (i = 0; i < ocnt; ++i)                                // calculating LUT entries
                             {
                                 value = OFstatic_cast(double, i) + absmin;
-                                *(q++) = OFstatic_cast(T3, outrange / (1 + exp(-4 * (value - center) / width)));
+                                *(q++) = OFstatic_cast(T3, outrange / (1 + exp(-4 * (value - center) / width)) + lowvalue);
                             }
                         }
                         const T3 *lut0 = lut - OFstatic_cast(T2, absmin);             // points to 'zero' entry
@@ -914,7 +917,7 @@ class DiMonoOutputPixelTemplate
                             for (i = Count; i != 0; --i)
                             {
                                 value = OFstatic_cast(double, *(p++));
-                                *(q++) = OFstatic_cast(T3, outrange / (1 + exp(-4 * (value - center) / width)));
+                                *(q++) = OFstatic_cast(T3, outrange / (1 + exp(-4 * (value - center) / width)) + lowvalue);
                             }
                         }
                     }
@@ -960,7 +963,8 @@ class DiMonoOutputPixelTemplate
                 const double width_1 = width - 1;
                 const double leftBorder = center - 0.5 - width_1 / 2;                 // window borders, according to supplement 33
                 const double rightBorder = center - 0.5 + width_1 / 2;
-                const double outrange = OFstatic_cast(double, high) - OFstatic_cast(double, low);  // output range
+                const double lowvalue = OFstatic_cast(double, low);
+                const double outrange = OFstatic_cast(double, high) - lowvalue;       // output range
                 const unsigned long ocnt = determineOptimizationCount(inter->getAbsMaxRange());    // number of LUT entries
                 const T1 *p = pixel + start;
                 T3 *q = Data;
@@ -1007,7 +1011,7 @@ class DiMonoOutputPixelTemplate
                                     value2 = pcnt - 1;                                // last LUT index
                                 else
                                     value2 = OFstatic_cast(Uint32, (value - leftBorder) * gradient1);
-                                *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value2)) * gradient2);
+                                *(q++) = OFstatic_cast(T3, lowvalue + OFstatic_cast(double, plut->getValue(value2)) * gradient2);
                             }
                         }
                         const T3 *lut0 = lut - OFstatic_cast(T2, absmin);             // points to 'zero' entry
@@ -1046,7 +1050,7 @@ class DiMonoOutputPixelTemplate
                                     value2 = pcnt - 1;                                // last LUT index
                                 else
                                     value2 = OFstatic_cast(Uint32, (value - leftBorder) * gradient1);
-                                *(q++) = OFstatic_cast(T3, OFstatic_cast(double, low) + OFstatic_cast(double, plut->getValue(value2)) * gradient2);
+                                *(q++) = OFstatic_cast(T3, lowvalue + OFstatic_cast(double, plut->getValue(value2)) * gradient2);
                             }
                         }
                     }
index dcc674ac0369310d882527e43f79f264ce73b40c..adeef55bb8338b44e8087201811fa202d7c08aea 100644 (file)
@@ -357,14 +357,16 @@ class DCMTK_DCMIMGLE_EXPORT DiOverlayPlane
      *  Overlay plane is clipped to the area specified by the four min/max coordinates.
      *  Memory isn't handled internally and must therefore be deleted from calling program.
      *
-     ** @param  frame  number of frame
-     *  @param  xmin   x-coordinate of the top left hand corner
-     *  @param  ymin   y-coordinate of the top left hand corner
-     *  @param  xmax   x-coordinate of the bottom right hand corner
-     *  @param  ymax   y-coordinate of the bottom right hand corner
-     *  @param  bits   number of bits (stored) in the resulting array
-     *  @param  fore   foreground color used for the plane (0x00-0xff)
-     *  @param  back   transparent background color (0x00-0xff)
+     ** @param  frame      number of frame
+     *  @param  xmin       x-coordinate of the top left hand corner
+     *  @param  ymin       y-coordinate of the top left hand corner
+     *  @param  xmax       x-coordinate of the bottom right hand corner
+     *  @param  ymax       y-coordinate of the bottom right hand corner
+     *  @param  bits       number of bits (stored) in the resulting array
+     *  @param  fore       foreground color used for the plane (0..2^bits-1)
+     *  @param  back       transparent background color (0..2^bits-1)
+     *  @param  useOrigin  use overlay plane's origin for calculating the start position
+     *                     if true (default), ignore it otherwise
      *
      ** @return pointer to pixel data if successful, NULL otherwise
      */
@@ -375,7 +377,8 @@ class DCMTK_DCMIMGLE_EXPORT DiOverlayPlane
                   const Uint16 ymax,
                   const int bits,
                   const Uint16 fore,
-                  const Uint16 back);
+                  const Uint16 back,
+                  const OFBool useOrigin = OFTrue);
 
     /** create overlay plane data in (6xxx,3000) format.
      *  (1 bit allocated and stored, foreground color is 1, background color is 0,
@@ -410,11 +413,14 @@ class DCMTK_DCMIMGLE_EXPORT DiOverlayPlane
 
     /** set internal 'cursor' to a specific position
      *
-     ** @param  x  new x-coordinate to start from
-     *  @param  y  new y-coordinate to start from
+     ** @param  x          new x-coordinate to start from
+     *  @param  y          new y-coordinate to start from
+     *  @param  useOrigin  use overlay plane's origin for calculating the start position
+     *                     if true (default), ignore it otherwise
      */
     inline void setStart(const Uint16 x,
-                         const Uint16 y);
+                         const Uint16 y,
+                         const OFBool useOrigin = OFTrue);
 
 
  protected:
@@ -547,15 +553,25 @@ inline int DiOverlayPlane::getNextBit()
 
 
 inline void DiOverlayPlane::setStart(const Uint16 x,
-                                     const Uint16 y)
+                                     const Uint16 y,
+                                     const OFBool useOrigin)
 {
-    if (BitsAllocated == 16)
-        Ptr = StartPtr + OFstatic_cast(unsigned long, y - Top) * OFstatic_cast(unsigned long, Columns) +
-            OFstatic_cast(unsigned long, x - Left);
-    else
-        BitPos = StartBitPos + (OFstatic_cast(unsigned long, y - Top) * OFstatic_cast(unsigned long, Columns) +
-            OFstatic_cast(unsigned long, x - Left)) * OFstatic_cast(unsigned long, BitsAllocated);
+    if (useOrigin)
+    {
+        if (BitsAllocated == 16)
+            Ptr = StartPtr + OFstatic_cast(unsigned long, y - Top) * OFstatic_cast(unsigned long, Columns) +
+                OFstatic_cast(unsigned long, x - Left);
+        else
+            BitPos = StartBitPos + (OFstatic_cast(unsigned long, y - Top) * OFstatic_cast(unsigned long, Columns) +
+                OFstatic_cast(unsigned long, x - Left)) * OFstatic_cast(unsigned long, BitsAllocated);
+    } else {
+        if (BitsAllocated == 16)
+            Ptr = StartPtr + OFstatic_cast(unsigned long, y) * OFstatic_cast(unsigned long, Columns) +
+                OFstatic_cast(unsigned long, x);
+        else
+            BitPos = StartBitPos + (OFstatic_cast(unsigned long, y) * OFstatic_cast(unsigned long, Columns) +
+                OFstatic_cast(unsigned long, x)) * OFstatic_cast(unsigned long, BitsAllocated);
+    }
 }
 
-
 #endif
index ee7cfc3b610ad702403039253ee524f13aa5ac34..5a1b19fe416c9e760e3482abf0965d4896a3f5d4 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1996-2018, OFFIS e.V.
+ *  Copyright (C) 1996-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -103,8 +103,11 @@ DiImage::DiImage(const DiDocument *docu,
         if (Document->getValue(DCM_FrameTime, ds))
         {
             if (ds <= 0)
-                DCMIMGLE_WARN("invalid value for 'FrameTime' (" << ds << ") ... ignoring");
-            else
+            {
+                /* there are rare cases, where a frame time of 0 makes sense */
+                if ((ds < 0) || (NumberOfFrames > 1))
+                    DCMIMGLE_WARN("invalid value for 'FrameTime' (" << ds << ") ... ignoring");
+            } else
                 FrameTime = ds;
         }
         FirstFrame = (docu->getFrameStart() < NumberOfFrames) ? docu->getFrameStart() : NumberOfFrames - 1;
index fce44fe01175fe1556abaa4e3c04e37b4375b418..cf91f1010d701cde26d8e0384ea17b8fd79e39da 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1996-2017, OFFIS e.V.
+ *  Copyright (C) 1996-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -576,7 +576,7 @@ void *DiOverlay::getFullPlaneData(const unsigned long frame,
         {
             width = op->getWidth();
             height = op->getHeight();
-            return op->getData(frame, 0, 0, width, height, bits, fore, back);
+            return op->getData(frame, 0, 0, width, height, bits, fore, back, OFFalse /*useOrigin*/);
         }
     }
     return NULL;
index d982f7cb233897acc9e7a66e1e020024048b27db..73def7f6f2acf10f2768cf76f368076c76def870 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1996-2018, OFFIS e.V.
+ *  Copyright (C) 1996-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -76,7 +76,7 @@ DiOverlayPlane::DiOverlayPlane(const DiDocument *docu,
     {
         /* determine first frame to be processed */
         FirstFrame = docu->getFrameStart();
-        /* specifiy overlay group number */
+        /* specify overlay group number */
         DcmTagKey tag(group, DCM_OverlayRows.getElement() /* dummy */);
         /* get descriptive data */
         tag.setElement(DCM_OverlayLabel.getElement());
@@ -349,7 +349,8 @@ void *DiOverlayPlane::getData(const unsigned long frame,
                               const Uint16 ymax,
                               const int bits,
                               const Uint16 fore,
-                              const Uint16 back)
+                              const Uint16 back,
+                              const OFBool useOrigin)
 {
     const unsigned long count = OFstatic_cast(unsigned long, xmax - xmin) * OFstatic_cast(unsigned long, ymax - ymin);
     if (Valid && (count > 0))
@@ -373,7 +374,7 @@ void *DiOverlayPlane::getData(const unsigned long frame,
                     {
                         for (y = ymin; y < ymax; ++y)
                         {
-                            setStart(xmin, y);
+                            setStart(xmin, y, useOrigin);
                             for (x = xmin; x < xmax; ++x)
                             {
                                 if (getNextBit())
@@ -418,7 +419,7 @@ void *DiOverlayPlane::getData(const unsigned long frame,
                     {
                         for (y = ymin; y < ymax; ++y)
                         {
-                            setStart(xmin, y);
+                            setStart(xmin, y, useOrigin);
                             for (x = xmin; x < xmax; ++x, ++q)
                             {
                                 if (getNextBit())
@@ -447,7 +448,7 @@ void *DiOverlayPlane::getData(const unsigned long frame,
                     {
                         for (y = ymin; y < ymax; ++y)
                         {
-                            setStart(xmin, y);
+                            setStart(xmin, y, useOrigin);
                             for (x = xmin; x < xmax; ++x, ++q)
                             {
                                 if (getNextBit())
index c956527a0b22dcd94c037d8a5a30498285ba66dd..24bc031e9044bdddd75487fee980142f80a289d4 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016-2018, Pascal Getreuer, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Pascal Getreuer, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define CIELABUTIL_H
 
 #include "dcmtk/config/osconfig.h"
-#define INCLUDE_CMATH                // for pow() function
-#include "dcmtk/ofstd/ofstdinc.h"
+#define INCLUDE_CMATH // for pow() function
 #include "dcmtk/dcmiod/ioddef.h"
-
+#include "dcmtk/ofstd/ofstdinc.h"
 
 /** Class supporting color space conversions from and to CIELab. In some IODs
  *  DICOM stores CIELab color values which must often be converted to RGB for
 class DCMTK_DCMIOD_EXPORT IODCIELabUtil
 {
 public:
-
-  /// D65 standard lightpoint X component for conversion from CIEXYZ to CIELab
-  static const double D65_WHITEPOINT_X;
-  /// D65 standard lightpoint Y component for conversion from CIEXYZ to CIELab
-  static const double D65_WHITEPOINT_Y;
-  /// D65 standard lightpoint Z component for conversion from CIEXYZ to CIELab
-  static const double D65_WHITEPOINT_Z;
-
-  /** Convert CIELab color representation as found in DICOM to sRGB value
-   *  representation. See DICOM part 3 for details.
-   *  @param  R Output sRGB "R" component (red) with 0 <= R <= 1
-   *  @param  G Output sRGB "G" component (green) with 0 <= G <= 1
-   *  @param  B Output sRGB "R" component (blue) with 0 <= B <= 1
-   *  @param  LDicom Input DICOM CIELab luminance component with 0 <= L <= 65535
-   *  @param  aDicom Input DICOM CIELab "a" component (red<->green) with 0 <= a <= 65535
-   *  @param  bDicom Input DICOM CIELab "b" component (blue<->yellow) with 0 <= a <= 65535
-   */
-  static void dicomLab2RGB(double& R, double& G, double& B, double LDicom, double aDicom, double bDicom);
-
-  /** Convert sRGB color representation to CIELab color representation as found
-   *  in DICOM. See DICOM part 3 for details.
-   *  @param  LDicom Output CIELab luminance component with 0 <= L <= 65535 as found
-   *          in DICOM
-   *  @param  aDicom Output CIELab "a" component (red<->green) with 0 <= a <= 65535
-   *          as found in DICOM
-   *  @param  bDicom Output CIELab "b" component (blue<->yellow) with 0 <= b <= 65535
-   *          as found in DICOM
-   *  @param  R Input sRGB "R" component (red) with 0 <= R <= 1
-   *  @param  G Input sRGB "G" component (green) with 0 <= G <= 1
-   *  @param  B Input sRGB "R" component (blue) with 0 <= B <= 1
-   *
-   */
-  static void rgb2DicomLab(double& LDicom, double& aDicom, double& bDicom, double R, double G, double B);
-
-  /** Convert CIELab color representation as found in DICOM to CIELab
-   *  representation. See DICOM part 3 for details.
-   *  @param  L Output CIELab luminance component with 0 <= L <= 100
-   *  @param  a Output CIELab "a" component (red<->green) with -127 <= a <= 128
-   *  @param  b Output CIELab "b" component (blue<->yellow) with -127 <= b <= 128
-   *  @param  LDicom Input CIELab luminance component with 0 <= L <= 65535 as found
-   *          in DICOM
-   *  @param  aDicom Input CIELab "a" component (red<->green) with 0 <= a <= 65535
-   *          as found in DICOM
-   *  @param  bDicom Input CIELab "b" component (blue<->yellow) with 0 <= b <= 65535
-   *          as found in DICOM
-   */
-  static void dicomlab2Lab(double& L, double& a, double& b, double LDicom, double aDicom, double bDicom);
-
-  /** Convert CIELab color representation to CIELab color representation found
-   *  in DICOM. See DICOM part 3 for details.
-   *  @param  LDicom Output CIELab luminance component with 0 <= L <= 65535 as found
-   *          in DICOM
-   *  @param  aDicom Output CIELab "a" component (red<->green) with 0 <= a <= 65535
-   *          as found in DICOM
-   *  @param  bDicom Output CIELab "b" component (blue<->yellow) with 0 <= b <= 65535
-   *          as found in DICOM
-   *  @param  L Input CIELab luminance component with 0 <= L <= 100
-   *  @param  a Input CIELab "a" component (red<->green) with -127 <= a <= 128
-   *  @param  b Input CIELab "b" component (blue<->yellow) with -127 <= b <= 128
-   *
-   */
-  static void lab2DicomLab(double& LDicom, double& aDicom, double& bDicom, double L, double a, double b);
-
-  /** Convert sRGB color representation to CIELab representation
-   *  @param  L Output CIELab luminance component with 0 <= L <= 100
-   *  @param  a Output CIELab "a" component (red<->green) with -127 <= a <= 128
-   *  @param  b Output CIELab "b" component (blue<->yellow) with -127 <= b <= 128
-   *  @param  R Input sRGB "R" component (red) with 0 <= R <= 1
-   *  @param  G Input sRGB "G" component (green) with 0 <= G <= 1
-   *  @param  B Input sRGB "R" component (blue) with 0 <= B <= 1
-   */
-  static void rgb2Lab(double& L, double& a, double& b, double R, double G, double B);
-
-  /** Convert sRGB color representation to CIE XYZ representation
-   *  @param  X Output CIELab XYZ "X" component with 0 <= X <= 1
-   *  @param  Y Output CIELab XYZ "Y" component with 0 <= Y <= 1
-   *  @param  Z Output CIELab XYZ "Z" component with 0 <= Z <= 1
-   *  @param  R Input sRGB "R" component (red) with 0 <= R <= 1
-   *  @param  G Input sRGB "G" component (green) with 0 <= G <= 1
-   *  @param  B Input sRGB "R" component (blue) with 0 <= B <= 1
-   */
-  static void rgb2Xyz(double& X, double& Y, double& Z, double R, double G, double B);
-
-
-  /** Convert CIELAB XYZ color representation to CIELab representation
-   *  @param  L Output CIELab luminance component with 0 <= L <= 100
-   *  @param  a Output CIELab "a" component (red<->green) with -127 <= a <= 128
-   *  @param  b Output CIELab "b" component (blue<->yellow) with -127 <= b <= 128
-   *  @param  X Input CIELab XYZ "X" component with 0 <= X <= 1
-   *  @param  Y Input CIELab XYZ "Y" component with 0 <= Y <= 1
-   *  @param  Z Input CIELab XYZ "Z" component with 0 <= Z <= 1
-   */
-  static void xyz2Lab(double& L, double& a, double& b, double X, double Y, double Z);
-
-  /** Convert CIELab color representation to sRGB representation
-   *  @param  R Output sRGB "R" component (red) with 0 <= R <= 1
-   *  @param  G Output sRGB "G" component (green) with 0 <= G <= 1
-   *  @param  B Output sRGB "R" component (blue) with 0 <= B <= 1
-   *  @param  L Input CIELab luminance component with 0 <= L <= 100
-   *  @param  a Input CIELab "a" component (red<->green) with -127 <= a <= 128
-   *  @param  b Input CIELab "b" component (blue<->yellow) with -127 <= b <= 128
-   */
-  static void lab2Rgb(double& R, double& G, double& B, double L, double a, double b);
-
-  /** Convert CIELab color representation to CIE XYZ representation
-   *  @param  X Output CIELab XYZ "X" component with 0 <= X <= 1
-   *  @param  Y Output CIELab XYZ "Y" component with 0 <= Y <= 1
-   *  @param  Z Output CIELab XYZ "Z" component with 0 <= Z <= 1
-   *  @param  L Input CIELab luminance component with 0 <= L <= 100
-   *  @param  a Input CIELab "a" component (red<->green) with -127 <= a <= 128
-   *  @param  b Input CIELab "b" component (blue<->yellow) with -127 <= b <= 128
-   */
-  static void lab2Xyz(double& X, double& Y, double& Z, double L, double a, double b);
-
-  /** Convert CIE XYZ color representation to sRGB representation
-   *  @param  R Output sRGB "R" component (red) with 0 <= R <= 1
-   *  @param  G Output sRGB "G" component (green) with 0 <= G <= 1
-   *  @param  B Output sRGB "R" component (blue) with 0 <= B <= 1
-   *  @param  X Output CIELab XYZ "X" component with 0 <= X <= 1
-   *  @param  Y Output CIELab XYZ "Y" component with 0 <= Y <= 1
-   *  @param  Z Output CIELab XYZ "Z" component with 0 <= Z <= 1
-   */
-  static void xyz2Rgb(double& R, double& G, double& B, double X, double Y, double Z);
+    /// D65 standard lightpoint X component for conversion from CIEXYZ to CIELab
+    static const double D65_WHITEPOINT_X;
+    /// D65 standard lightpoint Y component for conversion from CIEXYZ to CIELab
+    static const double D65_WHITEPOINT_Y;
+    /// D65 standard lightpoint Z component for conversion from CIEXYZ to CIELab
+    static const double D65_WHITEPOINT_Z;
+
+    /** Convert CIELab color representation as found in DICOM to sRGB value
+     *  representation. See DICOM part 3 for details.
+     *  @param  R Output sRGB "R" component (red) with 0 <= R <= 1
+     *  @param  G Output sRGB "G" component (green) with 0 <= G <= 1
+     *  @param  B Output sRGB "R" component (blue) with 0 <= B <= 1
+     *  @param  LDicom Input DICOM CIELab luminance component with 0 <= L <= 65535
+     *  @param  aDicom Input DICOM CIELab "a" component (red<->green) with 0 <= a <= 65535
+     *  @param  bDicom Input DICOM CIELab "b" component (blue<->yellow) with 0 <= a <= 65535
+     */
+    static void dicomLab2RGB(double& R, double& G, double& B, double LDicom, double aDicom, double bDicom);
+
+    /** Convert sRGB color representation to CIELab color representation as found
+     *  in DICOM. See DICOM part 3 for details.
+     *  @param  LDicom Output CIELab luminance component with 0 <= L <= 65535 as found
+     *          in DICOM
+     *  @param  aDicom Output CIELab "a" component (red<->green) with 0 <= a <= 65535
+     *          as found in DICOM
+     *  @param  bDicom Output CIELab "b" component (blue<->yellow) with 0 <= b <= 65535
+     *          as found in DICOM
+     *  @param  R Input sRGB "R" component (red) with 0 <= R <= 1
+     *  @param  G Input sRGB "G" component (green) with 0 <= G <= 1
+     *  @param  B Input sRGB "R" component (blue) with 0 <= B <= 1
+     *
+     */
+    static void rgb2DicomLab(double& LDicom, double& aDicom, double& bDicom, double R, double G, double B);
+
+    /** Convert CIELab color representation as found in DICOM to CIELab
+     *  representation. See DICOM part 3 for details.
+     *  @param  L Output CIELab luminance component with 0 <= L <= 100
+     *  @param  a Output CIELab "a" component (red<->green) with -127 <= a <= 128
+     *  @param  b Output CIELab "b" component (blue<->yellow) with -127 <= b <= 128
+     *  @param  LDicom Input CIELab luminance component with 0 <= L <= 65535 as found
+     *          in DICOM
+     *  @param  aDicom Input CIELab "a" component (red<->green) with 0 <= a <= 65535
+     *          as found in DICOM
+     *  @param  bDicom Input CIELab "b" component (blue<->yellow) with 0 <= b <= 65535
+     *          as found in DICOM
+     */
+    static void dicomlab2Lab(double& L, double& a, double& b, double LDicom, double aDicom, double bDicom);
+
+    /** Convert CIELab color representation to CIELab color representation found
+     *  in DICOM. See DICOM part 3 for details.
+     *  @param  LDicom Output CIELab luminance component with 0 <= L <= 65535 as found
+     *          in DICOM
+     *  @param  aDicom Output CIELab "a" component (red<->green) with 0 <= a <= 65535
+     *          as found in DICOM
+     *  @param  bDicom Output CIELab "b" component (blue<->yellow) with 0 <= b <= 65535
+     *          as found in DICOM
+     *  @param  L Input CIELab luminance component with 0 <= L <= 100
+     *  @param  a Input CIELab "a" component (red<->green) with -127 <= a <= 128
+     *  @param  b Input CIELab "b" component (blue<->yellow) with -127 <= b <= 128
+     *
+     */
+    static void lab2DicomLab(double& LDicom, double& aDicom, double& bDicom, double L, double a, double b);
+
+    /** Convert sRGB color representation to CIELab representation
+     *  @param  L Output CIELab luminance component with 0 <= L <= 100
+     *  @param  a Output CIELab "a" component (red<->green) with -127 <= a <= 128
+     *  @param  b Output CIELab "b" component (blue<->yellow) with -127 <= b <= 128
+     *  @param  R Input sRGB "R" component (red) with 0 <= R <= 1
+     *  @param  G Input sRGB "G" component (green) with 0 <= G <= 1
+     *  @param  B Input sRGB "R" component (blue) with 0 <= B <= 1
+     */
+    static void rgb2Lab(double& L, double& a, double& b, double R, double G, double B);
+
+    /** Convert sRGB color representation to CIE XYZ representation
+     *  @param  X Output CIELab XYZ "X" component with 0 <= X <= 1
+     *  @param  Y Output CIELab XYZ "Y" component with 0 <= Y <= 1
+     *  @param  Z Output CIELab XYZ "Z" component with 0 <= Z <= 1
+     *  @param  R Input sRGB "R" component (red) with 0 <= R <= 1
+     *  @param  G Input sRGB "G" component (green) with 0 <= G <= 1
+     *  @param  B Input sRGB "R" component (blue) with 0 <= B <= 1
+     */
+    static void rgb2Xyz(double& X, double& Y, double& Z, double R, double G, double B);
+
+    /** Convert CIELAB XYZ color representation to CIELab representation
+     *  @param  L Output CIELab luminance component with 0 <= L <= 100
+     *  @param  a Output CIELab "a" component (red<->green) with -127 <= a <= 128
+     *  @param  b Output CIELab "b" component (blue<->yellow) with -127 <= b <= 128
+     *  @param  X Input CIELab XYZ "X" component with 0 <= X <= 1
+     *  @param  Y Input CIELab XYZ "Y" component with 0 <= Y <= 1
+     *  @param  Z Input CIELab XYZ "Z" component with 0 <= Z <= 1
+     */
+    static void xyz2Lab(double& L, double& a, double& b, double X, double Y, double Z);
+
+    /** Convert CIELab color representation to sRGB representation
+     *  @param  R Output sRGB "R" component (red) with 0 <= R <= 1
+     *  @param  G Output sRGB "G" component (green) with 0 <= G <= 1
+     *  @param  B Output sRGB "R" component (blue) with 0 <= B <= 1
+     *  @param  L Input CIELab luminance component with 0 <= L <= 100
+     *  @param  a Input CIELab "a" component (red<->green) with -127 <= a <= 128
+     *  @param  b Input CIELab "b" component (blue<->yellow) with -127 <= b <= 128
+     */
+    static void lab2Rgb(double& R, double& G, double& B, double L, double a, double b);
+
+    /** Convert CIELab color representation to CIE XYZ representation
+     *  @param  X Output CIELab XYZ "X" component with 0 <= X <= 1
+     *  @param  Y Output CIELab XYZ "Y" component with 0 <= Y <= 1
+     *  @param  Z Output CIELab XYZ "Z" component with 0 <= Z <= 1
+     *  @param  L Input CIELab luminance component with 0 <= L <= 100
+     *  @param  a Input CIELab "a" component (red<->green) with -127 <= a <= 128
+     *  @param  b Input CIELab "b" component (blue<->yellow) with -127 <= b <= 128
+     */
+    static void lab2Xyz(double& X, double& Y, double& Z, double L, double a, double b);
+
+    /** Convert CIE XYZ color representation to sRGB representation
+     *  @param  R Output sRGB "R" component (red) with 0 <= R <= 1
+     *  @param  G Output sRGB "G" component (green) with 0 <= G <= 1
+     *  @param  B Output sRGB "R" component (blue) with 0 <= B <= 1
+     *  @param  X Output CIELab XYZ "X" component with 0 <= X <= 1
+     *  @param  Y Output CIELab XYZ "Y" component with 0 <= Y <= 1
+     *  @param  Z Output CIELab XYZ "Z" component with 0 <= Z <= 1
+     */
+    static void xyz2Rgb(double& R, double& G, double& B, double X, double Y, double Z);
 
 protected:
-
-  /** Perform sRGB gamma correction, transforms R to R'
-   *  @param  n The value to correct
-   *  @return The gamma-corrected value
-   */
-  static double gammaCorrection(double n);
-
-  /** Perform inverse sRGB gamma correction, transforms R' to R
-   *  @param  n The value to invert
-   *  @return The gamma-inverted value
-   */
-  static double invGammaCorrection(double n);
-
-  /** CIE L*a*b* f function (used to convert XYZ to L*a*b*)
-   *  @param  n value to convert
-   *  @return The converted value
-   */
-  static double labf(double n);
-
-  /** CIE L*a*b* inverse f function
-   *  @param n The value to compute the inverse for
-   *  @return The resulting inverse
-   */
-  static double labfInv(double n);
-
-  /** Get the minimum of two numbers
-   *  @param  a First number
-   *  @param  b Second number
-   *  @return The minimum of a, b. a if a and b are equal.
-   */
-  static double min2(double a, double b);
-
-  /** Get the minimum of three numbers
-   *  @param  a First number
-   *  @param  b Second number
-   *  @param  c Third number
-   *  @return The minimum of a, b and c. If a value occurs more than once,
-   *          then preference order then a is preferred if possible, b
-   *          otherwise
-   */
-  static double min3(double a, double b, double c);
-
+    /** Perform sRGB gamma correction, transforms R to R'
+     *  @param  n The value to correct
+     *  @return The gamma-corrected value
+     */
+    static double gammaCorrection(double n);
+
+    /** Perform inverse sRGB gamma correction, transforms R' to R
+     *  @param  n The value to invert
+     *  @return The gamma-inverted value
+     */
+    static double invGammaCorrection(double n);
+
+    /** CIE L*a*b* f function (used to convert XYZ to L*a*b*)
+     *  @param  n value to convert
+     *  @return The converted value
+     */
+    static double labf(double n);
+
+    /** CIE L*a*b* inverse f function
+     *  @param n The value to compute the inverse for
+     *  @return The resulting inverse
+     */
+    static double labfInv(double n);
+
+    /** Get the minimum of two numbers
+     *  @param  a First number
+     *  @param  b Second number
+     *  @return The minimum of a, b. a if a and b are equal.
+     */
+    static double min2(double a, double b);
+
+    /** Get the minimum of three numbers
+     *  @param  a First number
+     *  @param  b Second number
+     *  @param  c Third number
+     *  @return The minimum of a, b and c. If a value occurs more than once,
+     *          then preference order then a is preferred if possible, b
+     *          otherwise
+     */
+    static double min3(double a, double b, double c);
 };
 
 #endif // CIELABUTIL_H
index 5b5739d5e22040378ce9c4fcce3449f8e9b9a2c3..50d8973ec6a9132227b626b8999a609dcf09355b 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2017, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 
 #include "dcmtk/config/osconfig.h"
 #include "dcmtk/dcmiod/iodrules.h"
-#include "dcmtk/dcmiod/modpatient.h"
-#include "dcmtk/dcmiod/modpatientstudy.h"
-#include "dcmtk/dcmiod/modgeneralstudy.h"
+#include "dcmtk/dcmiod/modcommoninstanceref.h"
 #include "dcmtk/dcmiod/modequipment.h"
-#include "dcmtk/dcmiod/modgeneralseries.h"
 #include "dcmtk/dcmiod/modfor.h"
+#include "dcmtk/dcmiod/modgeneralseries.h"
+#include "dcmtk/dcmiod/modgeneralstudy.h"
+#include "dcmtk/dcmiod/modpatient.h"
+#include "dcmtk/dcmiod/modpatientstudy.h"
 #include "dcmtk/dcmiod/modsopcommon.h"
-#include "dcmtk/dcmiod/modcommoninstanceref.h"
 
 /** Interface class to those modules and data attributes  are common for many
  *  DICOM IODs. The class offers a dedicated API for getting and settings those
@@ -43,228 +43,227 @@ class DCMTK_DCMIOD_EXPORT DcmIODCommon
 {
 
 public:
-
-  /** Constructor
-   */
-  DcmIODCommon();
-
-  /** Copy Constructor
-   *  @param  rhs The object to copy from
-   */
-  DcmIODCommon(const DcmIODCommon& rhs);
-
-  /** Get rules handled by this IOD
-   *  @return The rules
-   */
-  OFshared_ptr<IODRules> getRules();
-
- /** Get item managed by this IOD
-  *  @return The item
-  */
-  OFshared_ptr<DcmItem> getData();
-
-  /** Get Patient Module
-   *  @return Reference to Patient Module
-   */
-  IODPatientModule& getPatient();
-
-  /** Get Patient Study Module
-   *  @return Reference to Patient Study Module
-   */
-  IODPatientStudyModule& getPatientStudy();
-
-  /** Get General Study Module
-   *  @return Reference to General Study Module
-   */
-  IODGeneralStudyModule& getStudy();
-
-  /** Get General Equipment Module
-   *  @return Reference to General Equipment Module
-   */
-  IODGeneralEquipmentModule& getEquipment();
-
-  /** Get Series Module
-   *  @return Reference to General Series Module
-   */
-  IODGeneralSeriesModule& getSeries();
-
-  /** Get Frame of Reference Module
-   *  @return Reference to Frame of Reference Module
-   */
-  IODFoRModule& getFrameOfReference();
-
-  /** Get SOP Common Module
-   *  @return Reference to SOP Common Module
-   */
-  IODSOPCommonModule& getSOPCommon();
-
-  /** Get Common Instance Reference Module
-   *  @return Common Instance Reference Module
-   */
-  IODCommonInstanceReferenceModule& getCommonInstanceReference();
-
-  /** Destructor
-    */
-  virtual ~DcmIODCommon();
-
-  /** Clear (removes) all attributes handled by the modules of this IOD.
-   *  IOD Rules are not reset.
-   */
-  virtual void clearData();
-
-  /** Create new study.
-   *  After generating a new Study Instance UID the method createNewSeries() is
-   *  called, i.e.\ also a new Series Instance UID and SOP instance UID are
-   *  generated.  This is a requirement of the DICOM standard. All other
-   *  study-related attributes from the study-level modules managed by this class
-   *  are cleared (as well as Series and Instance level attributes).
-   *  @param  clearEquipment  If OFTrue (default), also the equipment information is
-   *          cleared (General Equipment Module))
-   */
-  virtual void createNewStudy(const OFBool clearEquipment = OFTrue);
-
-  /** Create a new series.
-   *  After generating a new Series Instance UID the method
-   *  createNewSOPInstance() is called, i.e.\ Series-related attributes managed
-   *  by the series-level modules of this class are cleared, as well as
-   *  instance-level data.
-   *  @param  clearFoR If OFTrue (default), also the frame of reference is
-   *          cleared (FoR Module)
-   */
-  virtual void createNewSeries(const OFBool clearFoR = OFTrue);
-
-  /** Create a new SOP instance.
-   *  Generate a new SOP Instance UID and set the Instance Creation Date/Time
-   *  to the current date and time.
-   *  It could be used explicitly from the calling application if a new UID
-   *  should be created (this is the case if the Study Instance UID or Series
-   *  Instance UID has changed as well as any other attribute on the instance
-   *  level, e.g.\ image pixel data). Also clears other instance related data.
-   */
-  virtual void createNewSOPInstance();
-
-  /** Make sure that the IOD contains a SOP Instance, Series Instance and Study
-   *  Instance UID. They are created if empty. Invalid UIDs are corrected if
-   *  desired.
-   *  @param  correctInvalid If OFTrue, invalid instance UIDs will be replaced
-   *          by new ones
-   */
-  virtual void ensureInstanceUIDs(const OFBool correctInvalid = OFFalse);
-
-  /** Read data into this class.
-   *  Please note that the current content is also deleted if the reading
-   *  process fails. If the log stream is set and valid the reason for any
-   *  error might be obtained from the error/warning output. The reading
-   *  process will ignore missing attributes or values as possible in order
-   *  to read as as much as possible.
-   *  @param  dataset DICOM dataset from which the document should be read
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition read(DcmItem &dataset);
-
-  /** Import common module attributes from dataset but only read Patient, Study,
-   *  Series and/or Frame of Reference level portions. The current content
-   *  is not deleted before reading. If the log stream is set and valid the
-   *  reason for any error might be obtained from the error/warning output.
-   *  @param  dataset     Reference to DICOM dataset from which the document
-   *          should be read
-   *  @param  readPatient Read Patient-level information if OFTrue
-   *  @param  readStudy   Read Study-level information if OFTrue, including
-   *          equipment module
-   *  @param  readFoR     Read Frame of Reference information if OFTrue. See
-   *          also readSeries parameter.
-   *  @param  readSeries  Read Series-level information if OFTrue, always
-   *                      includes Frame of Reference, i.e.\ readFoR is
-   *                      considered to be OFTrue
-   *  @param  takeOverCharset If OFTrue (default), Specific Character Set is
-   *                          taken over from imported dataset. If it's not
-   *                          present or empty (invalid), the attribute will
-   *                          not be present in this class either.
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition importHierarchy(DcmItem& dataset,
-                                      const OFBool readPatient,
-                                      const OFBool readStudy,
-                                      const OFBool readFoR = OFFalse,
-                                      const OFBool readSeries = OFFalse,
-                                      const OFBool takeOverCharset = OFTrue);
-
-  /** CAUTION: Parameter order (readFoR and readSeries) changed compared to the
-   *  old import() function.
-   *  Import common module attributes from DICOM file but only read Patient, Study,
-   *  Series and/or Frame of Reference level portions. The current content
-   *  is not deleted before reading. If the log stream is set and valid the
-   *  reason for any error might be obtained from the error/warning output.
-   *  @param  filename The filename to read from.
-   *  @param  readPatient Read Patient-level information if OFTrue
-   *  @param  readStudy   Read Study-level information if OFTrue, including
-   *          equipment module
-   *  @param  readFoR     Read Frame of Reference information if OFTrue. See
-   *          also readSeries parameter.
-   *  @param  readSeries  Read Series-level information if OFTrue, always
-   *                      includes Frame of Reference, i.e.\ readFoR is
-   *                      considered to be OFTrue
-   *  @param  takeOverCharset If OFTrue (default), Specific Character Set is
-   *                          taken over from imported dataset. If it's not
-   *                          present or empty (invalid), the attribute will
-   *                          not be present in this class either.
-   *  @return EC_Normal if reading was successful (i.e.\ if any information could
-   *          be read), otherwise an error is returned
-   */
-  virtual OFCondition importHierarchy(const OFString& filename,
-                                      const OFBool readPatient,
-                                      const OFBool readStudy,
-                                      const OFBool readFoR = OFFalse,
-                                      const OFBool readSeries = OFFalse,
-                                      const OFBool takeOverCharset = OFTrue);
-
-  /** Write the attributes managed by this class to DICOM dataset.
-   *  @param dataset  Reference to DICOM dataset to which the current document
-   *                  should be  written. The dataset is not cleared
-   *                  before writing to it.
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition write(DcmItem &dataset);
-
+    /** Constructor
+     */
+    DcmIODCommon();
+
+    /** Copy Constructor
+     *  @param  rhs The object to copy from
+     */
+    DcmIODCommon(const DcmIODCommon& rhs);
+
+    /** Get rules handled by this IOD
+     *  @return The rules
+     */
+    OFshared_ptr<IODRules> getRules();
+
+    /** Get item managed by this IOD
+     *  @return The item
+     */
+    OFshared_ptr<DcmItem> getData();
+
+    /** Get Patient Module
+     *  @return Reference to Patient Module
+     */
+    IODPatientModule& getPatient();
+
+    /** Get Patient Study Module
+     *  @return Reference to Patient Study Module
+     */
+    IODPatientStudyModule& getPatientStudy();
+
+    /** Get General Study Module
+     *  @return Reference to General Study Module
+     */
+    IODGeneralStudyModule& getStudy();
+
+    /** Get General Equipment Module
+     *  @return Reference to General Equipment Module
+     */
+    IODGeneralEquipmentModule& getEquipment();
+
+    /** Get Series Module
+     *  @return Reference to General Series Module
+     */
+    IODGeneralSeriesModule& getSeries();
+
+    /** Get Frame of Reference Module
+     *  @return Reference to Frame of Reference Module
+     */
+    IODFoRModule& getFrameOfReference();
+
+    /** Get SOP Common Module
+     *  @return Reference to SOP Common Module
+     */
+    IODSOPCommonModule& getSOPCommon();
+
+    /** Get Common Instance Reference Module
+     *  @return Common Instance Reference Module
+     */
+    IODCommonInstanceReferenceModule& getCommonInstanceReference();
+
+    /** Destructor
+     */
+    virtual ~DcmIODCommon();
+
+    /** Clear (removes) all attributes handled by the modules of this IOD.
+     *  IOD Rules are not reset.
+     */
+    virtual void clearData();
+
+    /** Create new study.
+     *  After generating a new Study Instance UID the method createNewSeries() is
+     *  called, i.e.\ also a new Series Instance UID and SOP instance UID are
+     *  generated.  This is a requirement of the DICOM standard. All other
+     *  study-related attributes from the study-level modules managed by this class
+     *  are cleared (as well as Series and Instance level attributes).
+     *  @param  clearEquipment  If OFTrue (default), also the equipment information is
+     *          cleared (General Equipment Module))
+     */
+    virtual void createNewStudy(const OFBool clearEquipment = OFTrue);
+
+    /** Create a new series.
+     *  After generating a new Series Instance UID the method
+     *  createNewSOPInstance() is called, i.e.\ Series-related attributes managed
+     *  by the series-level modules of this class are cleared, as well as
+     *  instance-level data.
+     *  @param  clearFoR If OFTrue (default), also the frame of reference is
+     *          cleared (FoR Module)
+     */
+    virtual void createNewSeries(const OFBool clearFoR = OFTrue);
+
+    /** Create a new SOP instance.
+     *  Generate a new SOP Instance UID and set the Instance Creation Date/Time
+     *  to the current date and time.
+     *  It could be used explicitly from the calling application if a new UID
+     *  should be created (this is the case if the Study Instance UID or Series
+     *  Instance UID has changed as well as any other attribute on the instance
+     *  level, e.g.\ image pixel data). Also clears other instance related data.
+     */
+    virtual void createNewSOPInstance();
+
+    /** Make sure that the IOD contains a SOP Instance, Series Instance and Study
+     *  Instance UID. They are created if empty. Invalid UIDs are corrected if
+     *  desired.
+     *  @param  correctInvalid If OFTrue, invalid instance UIDs will be replaced
+     *          by new ones
+     */
+    virtual void ensureInstanceUIDs(const OFBool correctInvalid = OFFalse);
+
+    /** Read data into this class.
+     *  Please note that the current content is also deleted if the reading
+     *  process fails. If the log stream is set and valid the reason for any
+     *  error might be obtained from the error/warning output. The reading
+     *  process will ignore missing attributes or values as possible in order
+     *  to read as as much as possible.
+     *  @param  dataset DICOM dataset from which the document should be read
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition read(DcmItem& dataset);
+
+    /** Import common module attributes from dataset but only read Patient, Study,
+     *  Series and/or Frame of Reference level portions. The current content
+     *  is not deleted before reading. If the log stream is set and valid the
+     *  reason for any error might be obtained from the error/warning output.
+     *  @param  dataset     Reference to DICOM dataset from which the document
+     *          should be read
+     *  @param  readPatient Read Patient-level information if OFTrue
+     *  @param  readStudy   Read Study-level information if OFTrue, including
+     *          equipment module
+     *  @param  readFoR     Read Frame of Reference information if OFTrue. See
+     *          also readSeries parameter.
+     *  @param  readSeries  Read Series-level information if OFTrue, always
+     *                      includes Frame of Reference, i.e.\ readFoR is
+     *                      considered to be OFTrue
+     *  @param  takeOverCharset If OFTrue (default), Specific Character Set is
+     *                          taken over from imported dataset. If it's not
+     *                          present or empty (invalid), the attribute will
+     *                          not be present in this class either.
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition importHierarchy(DcmItem& dataset,
+                                        const OFBool readPatient,
+                                        const OFBool readStudy,
+                                        const OFBool readFoR         = OFFalse,
+                                        const OFBool readSeries      = OFFalse,
+                                        const OFBool takeOverCharset = OFTrue);
+
+    /** CAUTION: Parameter order (readFoR and readSeries) changed compared to the
+     *  old import() function.
+     *  Import common module attributes from DICOM file but only read Patient, Study,
+     *  Series and/or Frame of Reference level portions. The current content
+     *  is not deleted before reading. If the log stream is set and valid the
+     *  reason for any error might be obtained from the error/warning output.
+     *  @param  filename The filename to read from.
+     *  @param  readPatient Read Patient-level information if OFTrue
+     *  @param  readStudy   Read Study-level information if OFTrue, including
+     *          equipment module
+     *  @param  readFoR     Read Frame of Reference information if OFTrue. See
+     *          also readSeries parameter.
+     *  @param  readSeries  Read Series-level information if OFTrue, always
+     *                      includes Frame of Reference, i.e.\ readFoR is
+     *                      considered to be OFTrue
+     *  @param  takeOverCharset If OFTrue (default), Specific Character Set is
+     *                          taken over from imported dataset. If it's not
+     *                          present or empty (invalid), the attribute will
+     *                          not be present in this class either.
+     *  @return EC_Normal if reading was successful (i.e.\ if any information could
+     *          be read), otherwise an error is returned
+     */
+    virtual OFCondition importHierarchy(const OFString& filename,
+                                        const OFBool readPatient,
+                                        const OFBool readStudy,
+                                        const OFBool readFoR         = OFFalse,
+                                        const OFBool readSeries      = OFFalse,
+                                        const OFBool takeOverCharset = OFTrue);
+
+    /** Write the attributes managed by this class to DICOM dataset.
+     *  @param dataset  Reference to DICOM dataset to which the current document
+     *                  should be  written. The dataset is not cleared
+     *                  before writing to it.
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition write(DcmItem& dataset);
 
 private:
+    /** Copy assignment disabled
+     *  @param  rhs Object to copy from
+     *  @return Reference to "this" object
+     */
+    DcmIODCommon& operator=(const DcmIODCommon& rhs);
 
-  /** Copy assignment disabled
-   */
-  DcmIODCommon& operator=(const DcmIODCommon&);
-
-  /// The data hold by this class (shared with modules below)
-  OFshared_ptr<DcmItem> m_Item;
+    /// The data hold by this class (shared with modules below)
+    OFshared_ptr<DcmItem> m_Item;
 
-  /// The rules hold by this class (shared with modules below)
-  OFshared_ptr<IODRules> m_Rules;
+    /// The rules hold by this class (shared with modules below)
+    OFshared_ptr<IODRules> m_Rules;
 
-  /// Patient Module
-  IODPatientModule m_Patient;
+    /// Patient Module
+    IODPatientModule m_Patient;
 
-  /// Patient Study Module
-  IODPatientStudyModule m_PatientStudy;
+    /// Patient Study Module
+    IODPatientStudyModule m_PatientStudy;
 
-  /// General Study Module
-  IODGeneralStudyModule m_Study;
+    /// General Study Module
+    IODGeneralStudyModule m_Study;
 
-  /// General Equipment Module
-  IODGeneralEquipmentModule m_Equipment;
+    /// General Equipment Module
+    IODGeneralEquipmentModule m_Equipment;
 
-  /// General Series Module
-  IODGeneralSeriesModule m_Series;
+    /// General Series Module
+    IODGeneralSeriesModule m_Series;
 
-  /// Frame of Reference Module
-  IODFoRModule m_FrameOfReference;
+    /// Frame of Reference Module
+    IODFoRModule m_FrameOfReference;
 
-  /// SOP Common Module
-  IODSOPCommonModule m_SOPCommon;
+    /// SOP Common Module
+    IODSOPCommonModule m_SOPCommon;
 
-  /// Common Instance Reference Module
-  IODCommonInstanceReferenceModule m_CommonInstanceReferenceModule;
+    /// Common Instance Reference Module
+    IODCommonInstanceReferenceModule m_CommonInstanceReferenceModule;
 
-  /// Collects all modules of this class for convenience (iteration)
-  OFVector<IODModule*> m_Modules;
+    /// Collects all modules of this class for convenience (iteration)
+    OFVector<IODModule*> m_Modules;
 };
 
 #endif // IODCOMMN_H
index 8646e96fb3ffb66e320b31bc3d513b35a2c58fa3..f5c09c6d9c6fcbfaacf4cb45927e3d00b6bc562e 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define IODCONTENTITEMMACRO_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofmem.h"
-#include "dcmtk/dcmiod/iodrules.h"
-#include "dcmtk/dcmiod/modbase.h"
 #include "dcmtk/dcmiod/iodmacro.h"
+#include "dcmtk/dcmiod/iodrules.h"
 #include "dcmtk/dcmiod/iodtypes.h"
+#include "dcmtk/dcmiod/modbase.h"
+#include "dcmtk/ofstd/ofmem.h"
 
 /** Class representing the Content Item Macro:
  *
 class DCMTK_DCMIOD_EXPORT ContentItemMacro : public IODComponent
 {
 public:
-
-  enum ValueType
-  {
-     // Value is empty and not provided
-     VT_EMPTY,
-     // Value is provided but not known to the implementation
-     VT_UNKNOWN,
-     VT_DATE,
-     VT_TIME,
-     VT_DATETIME,
-     VT_PNAME,
-     VT_UIDREF,
-     VT_TEXT,
-     VT_CODE,
-     VT_NUMERIC,
-     VT_COMPOSITE,
-     VT_IMAGE
-   };
-
-  /** Class representing an item within the Content Item Macro's Referenced
-   *  SOP Sequence
-   */
-  class DCMTK_DCMIOD_EXPORT ReferencedSOPSequenceItem : public IODComponent
-  {
-  public:
+    enum ValueType
+    {
+        // Value is empty and not provided
+        VT_EMPTY,
+        // Value is provided but not known to the implementation
+        VT_UNKNOWN,
+        VT_DATE,
+        VT_TIME,
+        VT_DATETIME,
+        VT_PNAME,
+        VT_UIDREF,
+        VT_TEXT,
+        VT_CODE,
+        VT_NUMERIC,
+        VT_COMPOSITE,
+        VT_IMAGE
+    };
+
+    /** Class representing an item within the Content Item Macro's Referenced
+     *  SOP Sequence
+     */
+    class DCMTK_DCMIOD_EXPORT ReferencedSOPSequenceItem : public IODComponent
+    {
+    public:
+        /** Constructor
+         *  @param  item The item to be used for data storage. If NULL, the
+         *          class creates an empty data container.
+         *  @param  rules The rule set for this class. If NULL, the class creates
+         *          one from scratch and adds its values.
+         *  @param  parent The parent of the IOD component (NULL if none or unknown)
+         */
+        ReferencedSOPSequenceItem(OFshared_ptr<DcmItem> item,
+                                  OFshared_ptr<IODRules> rules,
+                                  IODComponent* parent = NULL);
+
+        /** Constructor
+         *  @param  parent The parent of the IOD component (NULL if none or unknown)
+         */
+        ReferencedSOPSequenceItem(IODComponent* parent = NULL);
+
+        /** Copy Constructor, performs deep copy
+         *  @param  rhs The parent of the IOD component (NULL if none or unknown)
+         */
+        ReferencedSOPSequenceItem(const ReferencedSOPSequenceItem& rhs);
+
+        /** Virtual Destructor
+         */
+        virtual ~ReferencedSOPSequenceItem();
+
+        /** Read attributes from given item into this class
+         *  @param source  The source to read from
+         *  @param clearOldData If OFTrue, old data is cleared before reading. Otherwise
+         *         old data is overwritten (or amended)
+         *  @result EC_Normal if reading was successful, error otherwise
+         */
+        virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+        /** Write attributes from this class into given item
+         *  @param  destination The item to write to
+         *  @result EC_Normal if writing was successful, error otherwise
+         */
+        virtual OFCondition write(DcmItem& destination);
+
+        /** Resets rules to their original values
+         */
+        virtual void resetRules();
+
+        /** Get name of macro
+         *  @return Name of the component ("ReferencedSOPSequenceItem")
+         */
+        virtual OFString getName() const;
+
+        /** Get SOPInstanceReferenceMacro
+         *  @return a reference to the included SOPInstanceReferenceMacro
+         */
+        virtual SOPInstanceReferenceMacro& getSOPInstanceReferenceMacro();
+
+        /** Get ReferencedFrameNumber
+         *  @param  value Reference to variable in which the value should be stored
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition getReferencedFrameNumber(OFString& value, const signed long pos = 0) const;
+
+        /** Get ReferencedSegmentNumber
+         *  @param  value Reference to variable in which the value should be stored
+         *  @param  pos Index of the value to get (0..vm-1)
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition getReferencedSegmentNumber(Uint16& value, const unsigned long pos = 0) const;
+
+        /** Set ReferencedFrameNumber
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value' for conformance with VR (IS) and VM (1-n) if enabled
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setReferencedFrameNumber(const OFString& value, const OFBool checkValue = OFTrue);
+
+        /** Set ReferencedSegmentNumber
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value' for conformance with VR (US) and VM (1-n) if enabled
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setReferencedSegmentNumber(const Uint16 value, const OFBool checkValue = OFTrue);
+
+    protected:
+        /// The name of this item ("ReferencedSOPSequenceItem")
+        static const OFString m_ComponentName;
+
+        /// SOP Instance Reference Macro
+        SOPInstanceReferenceMacro m_SOPInstanceReferenceMacro;
+    };
 
     /** Constructor
      *  @param  item The item to be used for data storage. If NULL, the
      *          class creates an empty data container.
      *  @param  rules The rule set for this class. If NULL, the class creates
      *          one from scratch and adds its values.
-     *  @param  parent The parent of the IOD component (NULL if none or unknown)
      */
-    ReferencedSOPSequenceItem(OFshared_ptr<DcmItem> item,
-                              OFshared_ptr<IODRules> rules,
-                              IODComponent* parent = NULL);
+    ContentItemMacro(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
 
     /** Constructor
-     *  @param  parent The parent of the IOD component (NULL if none or unknown)
      */
-    ReferencedSOPSequenceItem(IODComponent* parent = NULL);
+    ContentItemMacro();
 
-    /** Copy Constructor, performs deep copy
-     *  @param  rhs The parent of the IOD component (NULL if none or unknown)
+    /** Destructor
      */
-    ReferencedSOPSequenceItem(const ReferencedSOPSequenceItem& rhs);
+    virtual ~ContentItemMacro();
 
-    /** Virtual Destructor
+    ContentItemMacro(const ContentItemMacro& rhs);
+
+    /** Resets rules to their original values
      */
-    virtual ~ReferencedSOPSequenceItem();
+    virtual void resetRules();
+
+    /** Get name of module ("ContentItemMacro")
+     *  @return Name of the module ("ContentItemMacro")
+     */
+    virtual OFString getName() const;
 
     /** Read attributes from given item into this class
      *  @param source  The source to read from
@@ -107,8 +196,7 @@ public:
      *         old data is overwritten (or amended)
      *  @result EC_Normal if reading was successful, error otherwise
      */
-    virtual OFCondition read(DcmItem& source,
-                            const OFBool clearOldData = OFTrue);
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
 
     /** Write attributes from this class into given item
      *  @param  destination The item to write to
@@ -116,363 +204,241 @@ public:
      */
     virtual OFCondition write(DcmItem& destination);
 
-    /** Resets rules to their original values
+    /** Get ValueType
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual void resetRules();
+    virtual OFCondition getValueType(OFString& value, const signed long pos = 0) const;
 
-    /** Get name of macro
-     *  @return Name of the component ("ReferencedSOPSequenceItem")
+    /** Get ValueType
+     *  @param  value Reference to variable in which the value should be stored
+     *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFString getName() const;
+    virtual OFCondition getValueType(ValueType& value) const;
+
+    /** Get reference to the ConceptNameCodeSequence
+     *  @return a reference to the ConceptNameCodeSequence
+     */
+    virtual CodeSequenceMacro* getConceptNameCodeSequence();
+
+    /** Get a reference to the entire ConceptNameCodeSequence, including items
+     *  exceeding the value multiplicity restriction of "1"
+     *  @return a reference to the entire ConceptNameCodeSequence
+     */
+    virtual OFVector<CodeSequenceMacro*>& getEntireConceptNameCodeSequence();
+
+    /** Get DateTime
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getDateTime(OFString& value, const signed long pos = 0) const;
+
+    /** Get Date
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getDate(OFString& value, const signed long pos = 0) const;
 
-    /** Get SOPInstanceReferenceMacro
-     *  @return a reference to the included SOPInstanceReferenceMacro
+    /** Get Time
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getTime(OFString& value, const signed long pos = 0) const;
+
+    /** Get PersonName
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual SOPInstanceReferenceMacro& getSOPInstanceReferenceMacro();
+    virtual OFCondition getPersonName(OFString& value, const signed long pos = 0) const;
 
-    /** Get ReferencedFrameNumber
+    /** Get UID
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getReferencedFrameNumber(OFString &value,
-                                                 const signed long pos = 0) const;
+    virtual OFCondition getUID(OFString& value, const signed long pos = 0) const;
 
-    /** Get ReferencedSegmentNumber
+    /** Get TextValue
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getReferencedSegmentNumber(Uint16 &value,
-                                                   const signed long pos = 0) const;
+    virtual OFCondition getTextValue(OFString& value, const signed long pos = 0) const;
 
-    /** Set ReferencedFrameNumber
+    /** Get reference to the ConceptCodeSequence
+     *  @return a reference to the ConceptCodeSequence
+     */
+    virtual CodeSequenceMacro* getConceptCodeSequence();
+
+    /** Get a reference to the entire ConceptCodeSequence, including items
+     *  exceeding the value multiplicity restriction of "1"
+     *  @return a reference to the entire ConceptCodeSequence
+     */
+    virtual OFVector<CodeSequenceMacro*>& getEntireConceptCodeSequence();
+
+    /** Get NumericValue
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getNumericValue(OFString& value, const signed long pos = 0) const;
+
+    /** Get FloatingPointValue
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getFloatingPointValue(Float64& value, const unsigned long pos = 0) const;
+
+    /** Get RationalNumeratorValue
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getRationalNumeratorValue(Sint32& value, const unsigned long pos = 0) const;
+
+    /** Get RationalDenominatorValue
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getRationalDenominatorValue(Uint32& value, const unsigned long pos = 0) const;
+
+    /** Get reference to the MeasurementUnitsCodeSequence
+     *  @return a reference to the MeasurementUnitsCodeSequence
+     */
+    virtual CodeSequenceMacro* getMeasurementUnitsCodeSequence();
+
+    /** Get a reference to the entire MeasurementUnitsCodeSequence, including items
+     *  exceeding the value multiplicity restriction of "1"
+     *  @return a reference to the entire MeasurementUnitsCodeSequence
+     */
+    virtual OFVector<CodeSequenceMacro*>& getEntireMeasurementUnitsCodeSequence();
+
+    /** Get reference to the ReferencedSOPSequence
+     *  @return a reference to the ReferencedSOPSequence
+     */
+    virtual ReferencedSOPSequenceItem* getReferencedSOPSequence();
+
+    /** Get a reference to the entire ReferencedSOPSequence, including items
+     *  exceeding the value multiplicity restriction of "1"
+     *  @return a reference to the entire ReferencedSOPSequence
+     */
+    virtual OFVector<ReferencedSOPSequenceItem*>& getEntireReferencedSOPSequence();
+
+    /** Set ValueType
      *  @param  value Value to be set (single value only) or "" for no value
-     *  @param  checkValue Check 'value' for conformance with VR (IS) and VM (1-n) if enabled
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setReferencedFrameNumber(const OFString &value,
-                                                 const OFBool checkValue = OFTrue);
+    virtual OFCondition setValueType(const OFString& value, const OFBool checkValue = OFTrue);
 
-    /** Set ReferencedSegmentNumber
+    /** Set ValueType
      *  @param  value Value to be set (single value only) or "" for no value
-     *  @param  checkValue Check 'value' for conformance with VR (US) and VM (1-n) if enabled
+     *  @param  checkValue Check 'value'. Does nothing, here for consistency with
+     *          other set() functions.
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setReferencedSegmentNumber(const Uint16 value,
-                                                   const OFBool checkValue = OFTrue);
-
-  protected:
-
-    /// The name of this item ("ReferencedSOPSequenceItem")
-    static const OFString m_ComponentName;
-
-    /// SOP Instance Reference Macro
-    SOPInstanceReferenceMacro m_SOPInstanceReferenceMacro;
-  };
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  ContentItemMacro(OFshared_ptr<DcmItem> item,
-                   OFshared_ptr<IODRules> rules);
-
-  /** Constructor
-   */
-  ContentItemMacro();
-
-  /** Destructor
-   */
-  virtual ~ContentItemMacro();
-
-  ContentItemMacro(const ContentItemMacro& rhs);
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of module ("ContentItemMacro")
-   *  @return Name of the module ("ContentItemMacro")
-   */
-  virtual OFString getName() const;
-
-  /** Read attributes from given item into this class
-   *  @param source  The source to read from
-   *  @param clearOldData If OFTrue, old data is cleared before reading. Otherwise
-   *         old data is overwritten (or amended)
-   *  @result EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write attributes from this class into given item
-   *  @param  destination The item to write to
-   *  @result EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& destination);
-
-  /** Get ValueType
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getValueType(OFString &value,
-                                   const signed long pos = 0) const;
-
-  /** Get ValueType
-   *  @param  value Reference to variable in which the value should be stored
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getValueType(ValueType &value) const;
-
-  /** Get reference to the ConceptNameCodeSequence
-   *  @return a reference to the ConceptNameCodeSequence
-   */
-  virtual CodeSequenceMacro* getConceptNameCodeSequence();
-
-  /** Get a reference to the entire ConceptNameCodeSequence, including items
-   *  exceeding the value multiplicity restriction of "1"
-   *  @return a reference to the entire ConceptNameCodeSequence
-   */
-  virtual OFVector<CodeSequenceMacro*>& getEntireConceptNameCodeSequence();
-
-  /** Get DateTime
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getDateTime(OFString &value,
-                                  const signed long pos = 0) const;
-
-  /** Get Date
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getDate(OFString &value,
-                              const signed long pos = 0) const;
-
-  /** Get Time
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getTime(OFString &value,
-                              const signed long pos = 0) const;
-
-  /** Get PersonName
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getPersonName(OFString &value,
-                                    const signed long pos = 0) const;
-
-  /** Get UID
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getUID(OFString &value,
-                             const signed long pos = 0) const;
-
-  /** Get TextValue
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getTextValue(OFString &value,
-                                   const signed long pos = 0) const;
-
-  /** Get reference to the ConceptCodeSequence
-   *  @return a reference to the ConceptCodeSequence
-   */
-  virtual CodeSequenceMacro* getConceptCodeSequence();
-
-  /** Get a reference to the entire ConceptCodeSequence, including items
-   *  exceeding the value multiplicity restriction of "1"
-   *  @return a reference to the entire ConceptCodeSequence
-   */
-  virtual OFVector<CodeSequenceMacro*>& getEntireConceptCodeSequence();
-
-  /** Get NumericValue
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getNumericValue(OFString &value,
-                                      const signed long pos = 0) const;
-
-  /** Get FloatingPointValue
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getFloatingPointValue(Float64 &value,
-                                            const signed long pos = 0) const;
-
-  /** Get RationalNumeratorValue
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getRationalNumeratorValue(Sint32 &value,
-                                                const signed long pos = 0) const;
-
-  /** Get RationalDenominatorValue
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getRationalDenominatorValue(Uint32 &value,
-                                                  const signed long pos = 0) const;
-
-  /** Get reference to the MeasurementUnitsCodeSequence
-   *  @return a reference to the MeasurementUnitsCodeSequence
-   */
-  virtual CodeSequenceMacro* getMeasurementUnitsCodeSequence();
-
-  /** Get a reference to the entire MeasurementUnitsCodeSequence, including items
-   *  exceeding the value multiplicity restriction of "1"
-   *  @return a reference to the entire MeasurementUnitsCodeSequence
-   */
-  virtual OFVector<CodeSequenceMacro*>& getEntireMeasurementUnitsCodeSequence();
-
-  /** Get reference to the ReferencedSOPSequence
-   *  @return a reference to the ReferencedSOPSequence
-   */
-  virtual ReferencedSOPSequenceItem* getReferencedSOPSequence();
-
-  /** Get a reference to the entire ReferencedSOPSequence, including items
-   *  exceeding the value multiplicity restriction of "1"
-   *  @return a reference to the entire ReferencedSOPSequence
-   */
-  virtual OFVector<ReferencedSOPSequenceItem*>& getEntireReferencedSOPSequence();
-
-  /** Set ValueType
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setValueType(const OFString &value,
-                                   const OFBool checkValue = OFTrue);
-
-  /** Set ValueType
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value'. Does nothing, here for consistency with
-   *          other set() functions.
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setValueType(const ValueType value,
-                                   const OFBool checkValue = OFTrue);
-
-  /** Set DateTime
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (DT) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setDateTime(const OFString &value,
-                                  const OFBool checkValue = OFTrue);
-
-  /** Set Date
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (DA) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setDate(const OFString &value,
-                              const OFBool checkValue = OFTrue);
-
-  /** Set Time
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (TM) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setTime(const OFString &value,
-                              const OFBool checkValue = OFTrue);
-
-  /** Set PersonName
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (PN) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPersonName(const OFString &value,
-                                    const OFBool checkValue = OFTrue);
-
-  /** Set UID
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (UI) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setUID(const OFString &value,
-                             const OFBool checkValue = OFTrue);
-
-  /** Set TextValue
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (UT) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setTextValue(const OFString &value,
-                                   const OFBool checkValue = OFTrue);
-
-  /** Set NumericValue
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1-n) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setNumericValue(const OFString &value,
-                                      const OFBool checkValue = OFTrue);
-
-  /** Set FloatingPointValue
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  pos Index of the value to be set (starting from 0)
-   *  @param  checkValue Check 'value' for conformance with VR (FD) and VM (1-n) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setFloatingPointValue(const Float64 value,
-                                            const unsigned long pos = 0,
-                                            const OFBool checkValue = OFTrue);
-
-  /** Set RationalNumeratorValue
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  pos Index of the value to be set (starting from 0)
-   *  @param  checkValue Check 'value' for conformance with VR (SL) and VM (1-n) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRationalNumeratorValue(const Sint32 value,
-                                                const unsigned long pos = 0,
-                                                const OFBool checkValue = OFTrue);
-
-  /** Set RationalDenominatorValue
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  pos Index of the value to be set (starting from 0)
-   *  @param  checkValue Check 'value' for conformance with VR (UL) and VM (1-n) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRationalDenominatorValue(const Uint32 value,
-                                                  const unsigned long pos = 0,
-                                                  const OFBool checkValue = OFTrue);
-
-  virtual OFString toString();
+    virtual OFCondition setValueType(const ValueType value, const OFBool checkValue = OFTrue);
 
-protected:
+    /** Set DateTime
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (DT) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setDateTime(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Date
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (DA) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setDate(const OFString& value, const OFBool checkValue = OFTrue);
 
-  /// The name of this module ("ContentItemMacro")
-  static const OFString m_ModuleName;
+    /** Set Time
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (TM) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setTime(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set PersonName
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (PN) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPersonName(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set UID
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (UI) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setUID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set TextValue
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (UT) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setTextValue(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set NumericValue
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1-n) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setNumericValue(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set FloatingPointValue
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  pos Index of the value to be set (starting from 0)
+     *  @param  checkValue Check 'value' for conformance with VR (FD) and VM (1-n) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition
+    setFloatingPointValue(const Float64 value, const unsigned long pos = 0, const OFBool checkValue = OFTrue);
+
+    /** Set RationalNumeratorValue
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  pos Index of the value to be set (starting from 0)
+     *  @param  checkValue Check 'value' for conformance with VR (SL) and VM (1-n) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition
+    setRationalNumeratorValue(const Sint32 value, const unsigned long pos = 0, const OFBool checkValue = OFTrue);
+
+    /** Set RationalDenominatorValue
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  pos Index of the value to be set (starting from 0)
+     *  @param  checkValue Check 'value' for conformance with VR (UL) and VM (1-n) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition
+    setRationalDenominatorValue(const Uint32 value, const unsigned long pos = 0, const OFBool checkValue = OFTrue);
+
+    virtual OFString toString();
+
+protected:
+    /// The name of this module ("ContentItemMacro")
+    static const OFString m_ModuleName;
 
-  /// ConceptNameCodeSequence
-  OFVector<CodeSequenceMacro*> m_ConceptNameCodeSequence;
+    /// ConceptNameCodeSequence
+    OFVector<CodeSequenceMacro*> m_ConceptNameCodeSequence;
 
-  /// ConceptCodeSequence
-  OFVector<CodeSequenceMacro*> m_ConceptCodeSequence;
+    /// ConceptCodeSequence
+    OFVector<CodeSequenceMacro*> m_ConceptCodeSequence;
 
-  /// MeasurementUnitsCodeSequence
-  OFVector<CodeSequenceMacro*> m_MeasurementUnitsCodeSequence;
+    /// MeasurementUnitsCodeSequence
+    OFVector<CodeSequenceMacro*> m_MeasurementUnitsCodeSequence;
 
-  /// ReferencedSOPSequence
-  OFVector<ReferencedSOPSequenceItem*> m_ReferencedSOPSequence;
+    /// ReferencedSOPSequence
+    OFVector<ReferencedSOPSequenceItem*> m_ReferencedSOPSequence;
 };
 
 #endif // IODCONTENTITEMMACRO_H
index 1989579db49bf2d12b2f414cac271f085896a4cb..167488b71beca4ce3bf546a2da8c9d271a396228 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-
 #ifndef IODDEF_H
 #define IODDEF_H
 
 #include "dcmtk/config/osconfig.h"
 #include "dcmtk/ofstd/ofdefine.h"
 
-
 // Make sure DLL exports work for this module
 
 #ifdef dcmiod_EXPORTS
@@ -35,5 +33,4 @@
 #define DCMTK_DCMIOD_EXPORT DCMTK_DECL_IMPORT
 #endif
 
-
 #endif // IODDEF_H
index 2444edd9c6a16cbd414b152e07aca92d76938c53..3328186f9b61126937a7cfae267bb76b7eb0c935 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define IODIMAGE_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofutil.h"
-#include "dcmtk/ofstd/ofvriant.h"
 #include "dcmtk/dcmiod/iodcommn.h"
 #include "dcmtk/dcmiod/modgeneralimage.h"
 #include "dcmtk/dcmiod/modimagepixelvariant.h"
+#include "dcmtk/ofstd/ofutil.h"
+#include "dcmtk/ofstd/ofvriant.h"
 
 class IODDoubleFloatingPointImagePixelModule;
 class IODFloatingPointImagePixelModule;
-template<typename>
+template <typename>
 class IODImagePixelModule;
 
 /** Class for managing common image IOD attributes. At the moment support for
@@ -44,269 +44,269 @@ class IODImagePixelModule;
  *  Image Pixel Module.
  */
 #ifdef HAVE_CXX11
-template<typename T,typename... Types>
-struct DcmIODImageHasType
-: std::false_type {};
+template <typename T, typename... Types>
+struct DcmIODImageHasType : std::false_type
+{
+};
 
-template<typename T,typename... Types>
-struct DcmIODImageHasType<T,T,Types...>
-: std::true_type {};
+template <typename T, typename... Types>
+struct DcmIODImageHasType<T, T, Types...> : std::true_type
+{
+};
 
-template<typename T,typename T0,typename... Types>
-struct DcmIODImageHasType<T,T0,Types...>
-: DcmIODImageHasType<T,Types...>::type {};
+template <typename T, typename T0, typename... Types>
+struct DcmIODImageHasType<T, T0, Types...> : DcmIODImageHasType<T, Types...>::type
+{
+};
 
-template<typename... Types>
+template <typename... Types>
 #else
-template<OFVARIADIC_DECLARE_TEMPLATE_PARAMETER_PACK_WITH_DEFAULTS(T)>
+template <OFVARIADIC_DECLARE_TEMPLATE_PARAMETER_PACK_WITH_DEFAULTS(T)>
 #endif
 class DcmIODImage : public DcmIODCommon
 {
 
 public:
+    /** typedef for old compilers that do not define the type 'DcmIODImage' in
+     *  derived classes.
+     */
+    typedef DcmIODImage IODImage;
 
-  /** typedef for old compilers that do not define the type 'DcmIODImage' in
-   *  derived classes.
-   */
-  typedef DcmIODImage IODImage;
-
-  /** A good comment would be nice, but I have nothing in mind
-   */
+    /** A good comment would be nice, but I have nothing in mind
+     */
 #ifdef HAVE_CXX11
-  using IODImagePixelModuleType = IODImagePixelVariant<Types...>;
+    using IODImagePixelModuleType = IODImagePixelVariant<Types...>;
 #else
-  typedef IODImagePixelVariant<OFVARIADIC_TEMPLATE_PARAMETER_PACK(T)> IODImagePixelModuleType;
+    typedef IODImagePixelVariant<OFVARIADIC_TEMPLATE_PARAMETER_PACK(T)> IODImagePixelModuleType;
 #endif
 
-  /** Constructor, creates new DcmIODImage instance with integer-based pixel data.
-   */
-  DcmIODImage()
-  : DcmIODCommon()
-  , m_GeneralImage(getData(), getRules())
-  , m_ImagePixel()
-  {
-
-  }
-
-  /** Constructor, constructs new DcmIODImage instance with integer, float or
-   *  double based Image Pixel Module (i. e. Image Pixel Module, Floating Point
-   *  Image Pixel Module or the Double Floating Point Image Pixel Module), based
-   *  on the provided Image Pixel module type.
-   */
-  template<typename ImagePixel>
-  DcmIODImage(OFin_place_type_t(ImagePixel))
-  : DcmIODCommon()
-  , m_GeneralImage(getData(), getRules())
-  , m_ImagePixel(ImagePixel(getData(), getRules()))
-  {
-
-  }
-
-  /** Virtual Destructor
-   */
-  virtual ~DcmIODImage()
-  {
-
-  }
-
-  /** Get General Image Module
-   *  @return Reference to General Image Module
-   */
-  IODGeneralImageModule& getGeneralImage()
-  {
-    return m_GeneralImage;
-  }
-
-  /** Get Image Pixel Module (variant)
-   *  @return Reference to Image Pixel Module
-   */
-  IODImagePixelModuleType& getImagePixel()
-  {
-    return m_ImagePixel;
-  }
-
-  /** Clear (removes) all attributes handled by the modules of this IOD.
-   *  IOD Rules are not reset.
-   */
-  virtual void clearData()
-  {
-    DcmIODCommon::clearData();
-    m_GeneralImage.clearData();
-    m_ImagePixel.clearData();
-  }
-
-  /** Read common image module attributes (all those handled by this class)
-   *  from given item. Reads attributes from base class DcmIODCommon before.
-   *  The current content is deleted even if the reading process fails.
-   *  If the log stream is set and valid the reason for any error might be
-   *  obtained from the error/warning output.
-   *  @param  dataset  Reference to DICOM dataset from which the document
-   *          should be read
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition read(DcmItem &dataset)
-  {
-     // re-initialize object
-     clearData();
-
-     // read from base classes
-     DcmIODCommon::read(dataset);
-     m_GeneralImage.read(dataset, OFTrue /* clear old data */);
-
-     return readFloatingPointDoubleImagePixel<IODDoubleFloatingPointImagePixelModule>(dataset);
-  }
-
-  /** Write current common image module's attributes to DICOM dataset. Also
-   *  writes attributes of base class DcmIODCommon afterwards.
-   *  @param  dataset Reference to DICOM dataset to which the current data
-   *          should be written. The dataset is not cleared before writing
-   *          to it!
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition write(DcmItem &dataset)
-  {
-    OFCondition result = EC_Normal;
-
-    // Write base class attributes to dataset
-    result = DcmIODCommon::write(dataset);
-
-    // Write extra modules to dataset
-    if (result.good())
-      result = m_GeneralImage.write(dataset);
-    if (result.good())
-      result = m_ImagePixel.write(dataset);
-
-    return result;
-  }
+    /** Constructor, creates new DcmIODImage instance with integer-based pixel data.
+     */
+    DcmIODImage()
+        : DcmIODCommon()
+        , m_GeneralImageModuleEnabled(OFTrue)
+        , m_GeneralImage(getData(), getRules())
+        , m_ImagePixel()
+    {
+    }
 
-private:
+    /** Constructor, constructs new DcmIODImage instance with integer, float or
+     *  double based Image Pixel Module (i. e. Image Pixel Module, Floating Point
+     *  Image Pixel Module or the Double Floating Point Image Pixel Module), based
+     *  on the provided Image Pixel module type.
+     */
+    template <typename ImagePixel>
+    DcmIODImage(OFin_place_type_t(ImagePixel))
+        : DcmIODCommon()
+        , m_GeneralImageModuleEnabled(OFTrue)
+        , m_GeneralImage(getData(), getRules())
+        , m_ImagePixel(ImagePixel(getData(), getRules()))
+    {
+    }
+
+    /** Virtual Destructor
+     */
+    virtual ~DcmIODImage()
+    {
+    }
+
+    virtual void setGeneralImageModuleEnabled(const OFBool enabled)
+    {
+        m_GeneralImageModuleEnabled = enabled;
+    }
+
+    virtual OFBool getGeneralImageModuleEnabled() const
+    {
+        return m_GeneralImageModuleEnabled;
+    }
+
+    /** Get General Image Module
+     *  @return Reference to General Image Module
+     */
+    IODGeneralImageModule& getGeneralImage()
+    {
+        return m_GeneralImage;
+    }
+
+    /** Get Image Pixel Module (variant)
+     *  @return Reference to Image Pixel Module
+     */
+    IODImagePixelModuleType& getImagePixel()
+    {
+        return m_ImagePixel;
+    }
+
+    /** Clear (removes) all attributes handled by the modules of this IOD.
+     *  IOD Rules are not reset.
+     */
+    virtual void clearData()
+    {
+        DcmIODCommon::clearData();
+        m_GeneralImage.clearData();
+        m_ImagePixel.clearData();
+    }
+
+    /** Read common image module attributes (all those handled by this class)
+     *  from given item. Reads attributes from base class DcmIODCommon before.
+     *  The current content is deleted even if the reading process fails.
+     *  If the log stream is set and valid the reason for any error might be
+     *  obtained from the error/warning output.
+     *  @param  dataset  Reference to DICOM dataset from which the document
+     *          should be read
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition read(DcmItem& dataset)
+    {
+        // re-initialize object
+        clearData();
+
+        // read from base classes
+        DcmIODCommon::read(dataset);
+        if (m_GeneralImageModuleEnabled)
+        {
+            m_GeneralImage.read(dataset, OFTrue /* clear old data */);
+        }
+
+        return readFloatingPointDoubleImagePixel<IODDoubleFloatingPointImagePixelModule>(dataset);
+    }
+
+    /** Write current common image module's attributes to DICOM dataset. Also
+     *  writes attributes of base class DcmIODCommon afterwards.
+     *  @param  dataset Reference to DICOM dataset to which the current data
+     *          should be written. The dataset is not cleared before writing
+     *          to it!
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition write(DcmItem& dataset)
+    {
+        OFCondition result = EC_Normal;
+
+        // Write base class attributes to dataset
+        result = DcmIODCommon::write(dataset);
+
+        // Write extra modules to dataset
+        if (result.good() && m_GeneralImageModuleEnabled)
+            result = m_GeneralImage.write(dataset);
+        if (result.good())
+            result = m_ImagePixel.write(dataset);
+
+        return result;
+    }
 
-  template<typename T>
+private:
+    template <typename T>
 #ifdef HAVE_CXX11
-  typename std::enable_if<DcmIODImageHasType<T,Types...>::value,OFCondition>::type
+    typename std::enable_if<DcmIODImageHasType<T, Types...>::value, OFCondition>::type
 #else
-  OFTypename OFenable_if
-  <
-    (OFvariadic_find_type<T,OFVARIADIC_TEMPLATE_PARAMETER_PACK(T)>::value != -1),
-    OFCondition
-  >::type
+    OFTypename
+        OFenable_if<(OFvariadic_find_type<T, OFVARIADIC_TEMPLATE_PARAMETER_PACK(T)>::value != -1), OFCondition>::type
 #endif
-  readFloatingPointDoubleImagePixel(DcmItem& dataset)
-  {
-    if (dataset.tagExists(DCM_DoubleFloatPixelData))
-      return OFget<T>(&(m_ImagePixel = T(getData(),getRules())))->read(dataset);
-    return readFloatingPointImagePixel<IODFloatingPointImagePixelModule>(dataset);
-  }
-
-  template<typename T>
+    readFloatingPointDoubleImagePixel(DcmItem& dataset)
+    {
+        if (dataset.tagExists(DCM_DoubleFloatPixelData))
+            return OFget<T>(&(m_ImagePixel = T(getData(), getRules())))->read(dataset);
+        return readFloatingPointImagePixel<IODFloatingPointImagePixelModule>(dataset);
+    }
+
+    template <typename T>
 #ifdef HAVE_CXX11
-  typename std::enable_if<!DcmIODImageHasType<T,Types...>::value,OFCondition>::type
+    typename std::enable_if<!DcmIODImageHasType<T, Types...>::value, OFCondition>::type
 #else
-  OFTypename OFenable_if
-  <
-    (OFvariadic_find_type<T,OFVARIADIC_TEMPLATE_PARAMETER_PACK(T)>::value == -1),
-    OFCondition
-  >::type
+    OFTypename
+        OFenable_if<(OFvariadic_find_type<T, OFVARIADIC_TEMPLATE_PARAMETER_PACK(T)>::value == -1), OFCondition>::type
 #endif
-  readFloatingPointDoubleImagePixel(DcmItem& dataset)
-  {
-    return readFloatingPointImagePixel<IODFloatingPointImagePixelModule>(dataset);
-  }
+    readFloatingPointDoubleImagePixel(DcmItem& dataset)
+    {
+        return readFloatingPointImagePixel<IODFloatingPointImagePixelModule>(dataset);
+    }
 
-  template<typename T>
+    template <typename T>
 #ifdef HAVE_CXX11
-  typename std::enable_if<DcmIODImageHasType<T,Types...>::value,OFCondition>::type
+    typename std::enable_if<DcmIODImageHasType<T, Types...>::value, OFCondition>::type
 #else
-  OFTypename OFenable_if
-  <
-    (OFvariadic_find_type<T,OFVARIADIC_TEMPLATE_PARAMETER_PACK(T)>::value != -1),
-    OFCondition
-  >::type
+    OFTypename
+        OFenable_if<(OFvariadic_find_type<T, OFVARIADIC_TEMPLATE_PARAMETER_PACK(T)>::value != -1), OFCondition>::type
 #endif
-  readFloatingPointImagePixel(DcmItem& dataset)
-  {
-    if (dataset.tagExists(DCM_FloatPixelData))
-      return OFget<T>(&(m_ImagePixel = T(getData(),getRules())))->read(dataset);
-    return readIntegerImagePixel(dataset);
-  }
-
-  template<typename T>
+    readFloatingPointImagePixel(DcmItem& dataset)
+    {
+        if (dataset.tagExists(DCM_FloatPixelData))
+            return OFget<T>(&(m_ImagePixel = T(getData(), getRules())))->read(dataset);
+        return readIntegerImagePixel(dataset);
+    }
+
+    template <typename T>
 #ifdef HAVE_CXX11
-  typename std::enable_if<!DcmIODImageHasType<T,Types...>::value,OFCondition>::type
+    typename std::enable_if<!DcmIODImageHasType<T, Types...>::value, OFCondition>::type
 #else
-  OFTypename OFenable_if
-  <
-    (OFvariadic_find_type<T,OFVARIADIC_TEMPLATE_PARAMETER_PACK(T)>::value == -1),
-    OFCondition
-  >::type
+    OFTypename
+        OFenable_if<(OFvariadic_find_type<T, OFVARIADIC_TEMPLATE_PARAMETER_PACK(T)>::value == -1), OFCondition>::type
 #endif
-  readFloatingPointImagePixel(DcmItem& dataset)
-  {
-    return readIntegerImagePixel(dataset);
-  }
-
-  OFCondition readIntegerImagePixel(DcmItem& dataset)
-  {
-    Uint16 allocated, representation;
-    if
-    (
-      dataset.tagExists(DCM_PixelData) &&
-      dataset.findAndGetUint16(DCM_BitsAllocated, allocated).good() &&
-      dataset.findAndGetUint16(DCM_PixelRepresentation, representation).good()
-    )
-    switch ((allocated > 8 ? 2 : 0) | (representation ? 1 : 0))
+    readFloatingPointImagePixel(DcmItem& dataset)
+    {
+        return readIntegerImagePixel(dataset);
+    }
+
+    OFCondition readIntegerImagePixel(DcmItem& dataset)
     {
-    case 0:
-      return readImagePixel<Uint8>(dataset);
-    case 1:
-      return readImagePixel<Sint8>(dataset);
-    case 2:
-      return readImagePixel<Uint16>(dataset);
-    case 3:
-      return readImagePixel<Sint16>(dataset);
-    default:
-      break;
+        Uint16 allocated, representation;
+        // Pixel data is not managed right now by Image Pixel Module class.
+        if (/*  dataset.tagExists(DCM_PixelData) && */ dataset.findAndGetUint16(DCM_BitsAllocated, allocated).good()
+            && dataset.findAndGetUint16(DCM_PixelRepresentation, representation).good())
+            switch ((allocated > 8 ? 2 : 0) | (representation ? 1 : 0))
+            {
+                case 0:
+                    return readImagePixel<Uint8>(dataset);
+                case 1:
+                    return readImagePixel<Sint8>(dataset);
+                case 2:
+                    return readImagePixel<Uint16>(dataset);
+                case 3:
+                    return readImagePixel<Sint16>(dataset);
+                default:
+                    break;
+            }
+        return IOD_EC_InvalidPixelData;
     }
-    return IOD_EC_InvalidPixelData;
-  }
 
-  template<typename T>
+    template <typename T>
 #ifdef HAVE_CXX11
-  typename std::enable_if<DcmIODImageHasType<IODImagePixelModule<T>,Types...>::value,OFCondition>::type
+    typename std::enable_if<DcmIODImageHasType<IODImagePixelModule<T>, Types...>::value, OFCondition>::type
 #else
-  OFTypename OFenable_if
-  <
-    (OFvariadic_find_type<IODImagePixelModule<T>,OFVARIADIC_TEMPLATE_PARAMETER_PACK(T)>::value != -1),
-    OFCondition
-  >::type
+    OFTypename
+        OFenable_if<(OFvariadic_find_type<IODImagePixelModule<T>, OFVARIADIC_TEMPLATE_PARAMETER_PACK(T)>::value != -1),
+                    OFCondition>::type
 #endif
-  readImagePixel(DcmItem& dataset)
-  {
-    return OFget<IODImagePixelModule<T> >(&(m_ImagePixel = IODImagePixelModule<T>(getData(),getRules())))->read(dataset);
-  }
+    readImagePixel(DcmItem& dataset)
+    {
+        return OFget<IODImagePixelModule<T> >(&(m_ImagePixel = IODImagePixelModule<T>(getData(), getRules())))
+            ->read(dataset);
+    }
 
-  template<typename T>
+    template <typename T>
 #ifdef HAVE_CXX11
-  typename std::enable_if<!DcmIODImageHasType<IODImagePixelModule<T>,Types...>::value,OFCondition>::type
+    typename std::enable_if<!DcmIODImageHasType<IODImagePixelModule<T>, Types...>::value, OFCondition>::type
 #else
-  OFTypename OFenable_if
-  <
-    (OFvariadic_find_type<IODImagePixelModule<T>,OFVARIADIC_TEMPLATE_PARAMETER_PACK(T)>::value == -1),
-    OFCondition
-  >::type
+    OFTypename
+        OFenable_if<(OFvariadic_find_type<IODImagePixelModule<T>, OFVARIADIC_TEMPLATE_PARAMETER_PACK(T)>::value == -1),
+                    OFCondition>::type
 #endif
-  readImagePixel(DcmItem& dataset)
-  {
-    // Avoid compiler warning about unused parameter
-    OFstatic_cast(void, dataset);
-    return IOD_EC_InvalidPixelData;
-  }
-
-  /// General Image Module
-  IODGeneralImageModule m_GeneralImage;
-
-  /// Image Pixel Module
-  IODImagePixelModuleType m_ImagePixel;
+    readImagePixel(DcmItem& dataset)
+    {
+        // Avoid compiler warning about unused parameter
+        OFstatic_cast(void, dataset);
+        return IOD_EC_InvalidPixelData;
+    }
+
+    /// Denotes whether General Image Module is used in this class (OFTrue) or not (OFFalse).
+    /// This switch can be configured using a call to setGeneralImageModuleEnabled(). The
+    /// default is OFTrue.
+    OFBool m_GeneralImageModuleEnabled;
+
+    /// General Image Module
+    IODGeneralImageModule m_GeneralImage;
+
+    /// Image Pixel Module
+    IODImagePixelModuleType m_ImagePixel;
 };
 
 #endif // IODIMAGE_H
index 4430c2cda31f6c349a5a71f886ae2d51f9a756e3..bfa29184fed3800fa9ca35104554b5659da68e58 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2017, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define IODMACRO_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofvector.h"
-#include "dcmtk/ofstd/ofstring.h"
-#include "dcmtk/dcmdata/dctk.h"  // For VR classes, i.e. DcmCodeString etc.
+#include "dcmtk/dcmdata/dctk.h" // For VR classes, i.e. DcmCodeString etc.
 #include "dcmtk/dcmiod/iodrules.h"
 #include "dcmtk/dcmiod/modbase.h"
+#include "dcmtk/ofstd/ofstring.h"
+#include "dcmtk/ofstd/ofvector.h"
 
 /** Class representing a Code Sequence Macro
  */
@@ -35,166 +35,220 @@ class DCMTK_DCMIOD_EXPORT CodeSequenceMacro : public IODComponent
 {
 
 public:
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     *  @param  parent The parent of the IOD component (NULL if none or unknown)
+     */
+    CodeSequenceMacro(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules, IODComponent* parent = NULL);
+
+    /** Constructor
+     *  @param  parent The parent of the IOD component (NULL if none or unknown)
+     */
+    CodeSequenceMacro(IODComponent* parent = NULL);
+
+    /** Copy Constructor, performs deep copy
+     *  @param  rhs The parent of the IOD component (NULL if none or unknown)
+     */
+    CodeSequenceMacro(const CodeSequenceMacro& rhs);
+
+    /** Convenience constructor to set initial values
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     *  @param  parent The parent of the IOD component (NULL if none or unknown)
+     *  @param  codeValue The code value
+     *  @param  codingSchemeDesignator The coding scheme designator
+     *  @param  codeMeaning The code meaning
+     *  @param  codingSchemeVersion The coding scheme version (might be empty if
+     *          coding scheme is unique)
+     */
+    CodeSequenceMacro(OFshared_ptr<DcmItem> item,
+                      OFshared_ptr<IODRules> rules,
+                      IODComponent* parent,
+                      const OFString& codeValue,
+                      const OFString& codingSchemeDesignator,
+                      const OFString& codeMeaning,
+                      const OFString& codingSchemeVersion = "");
+
+    /** Convenience constructor to set initial values
+     *  @param  codeValue The code value
+     *  @param  codingSchemeDesignator The coding scheme designator
+     *  @param  codeMeaning The code meaning
+     *  @param  codingSchemeVersion The coding scheme version (might be empty if
+     *          coding scheme is unique)
+     *  @param  parent The parent of the IOD component (NULL if none or unknown)
+     */
+    CodeSequenceMacro(const OFString& codeValue,
+                      const OFString& codingSchemeDesignator,
+                      const OFString& codeMeaning,
+                      const OFString& codingSchemeVersion = "",
+                      IODComponent* parent                = NULL);
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of macro
+     *  @return Name of the component ("CodeSequenceMacro")
+     */
+    virtual OFString getName() const;
+
+    /** Virtual Destructor
+     */
+    virtual ~CodeSequenceMacro();
+
+    /** Check whether this component's data satisfies the underlying
+     *  rules. In this case, it is only checked that Designator, Value and
+     *  Meaning of the code are set.
+     *  @param  quiet If OFTrue, not error / warning messages will be produced. Only
+     *                the returned error code will indicate error or OK. Per default,
+     *                logging output is produced (OFFalse).
+     *  @result EC_Normal if rules are satisfied, error otherwise
+     */
+    virtual OFCondition check(const OFBool quiet = OFFalse);
+
+    /** Get Code Value, URL Code Value or Long Code Value
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @param  autoTag If OFTrue, this method will consider tags
+     *                  Code Value (0008,0100)
+     *                  URN Code Code Value (0008,0120) and
+     *                  Long Code Value (0008,0119) and
+     *                  in this order and will return once it finds that tag,
+     *                  even if the related value is empty.
+     *                  If OFFalse, getCodeValue() only returns the value
+     *                  found in Code Value (0008,0100).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getCodeValue(OFString& value, const signed long pos = 0, const OFBool autoTag = OFTrue);
+
+    /** Get URN Code Value
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getURNCodeValue(OFString& value, const signed long pos = 0);
+
+    /** Get Long Code Value
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getLongCodeValue(OFString& value, const signed long pos = 0);
+
+    /** Get Coding Scheme Designator
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos   Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getCodingSchemeDesignator(OFString& value, const signed long pos = 0);
+
+    /** Get Coding Scheme Version
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return  EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getCodingSchemeVersion(OFString& value, const signed long pos = 0);
+
+    /** Get Code Meaning
+     *  @param  value  Reference to variable in which the value should be stored
+     *  @param  pos    Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getCodeMeaning(OFString& value, const signed long pos = 0);
+
+    /** Returns whether code is empty, i.e. no component of the Code Sequence Macro
+     *  is set. This can be used in order to find out whether someone actually
+     *  wanted to fill in a valid code as opposed of leaving it unset.
+     *  @return OFTrue if no component of this class is set, OFFalse otherwise.
+     */
+    virtual OFBool empty();
+
+    /** Set Code Value
+     *  @param  value The value to set
+     *  @param  checkValue If OFTrue, VM and VR of value are checked
+     *  @param  autoTag If OFTrue, it is determined automatically if
+     *          tag Code Value, URN Code Value or Long Code Value is used.
+     *          If OFFalse, the classic Code Value is used.
+     *          Default is OFTrue.
+     *  @return EC_Normal if setting was successful, error otherwise
+     */
+    virtual OFCondition
+    setCodeValue(const OFString& value, const OFBool checkValue = OFTrue, const OFBool autoTag = OFTrue);
+
+    /** Set URN Code Value
+     *  @param  value The value to set
+     *  @param  checkValue If OFTrue, VM and VR of value are checked
+     *  @return EC_Normal if setting was successful, error otherwise
+     */
+    virtual OFCondition setURNCodeValue(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Long Code Value
+     *  @param  value The value to set
+     *  @param  checkValue If OFTrue, VM and VR of value are checked
+     *  @return EC_Normal if setting was successful, error otherwise
+     */
+    virtual OFCondition setLongCodeValue(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Coding Scheme Designator
+     *  @param  value The value to set
+     *  @param  checkValue If OFTrue, VM and VR of value are checked
+     *  @return EC_Normal if setting was successful, error otherwise
+     */
+    virtual OFCondition setCodingSchemeDesignator(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Coding Scheme Version
+     *  @param  value The value to set
+     *  @param  checkValue If OFTrue, VM and VR of value are checked
+     *  @return EC_Normal if setting was successful, error otherwise
+     */
+    virtual OFCondition setCodingSchemeVersion(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Code Meaning
+     *  @param  value The value to set
+     *  @param  checkValue If OFTrue, VM and VR of value are checked
+     *  @return EC_Normal if setting was successful, error otherwise
+     */
+    virtual OFCondition setCodeMeaning(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set all values in this class conveniently
+     *  @param  value Code Value to set
+     *  @param  scheme Coding Scheme Designator to set
+     *  @param  meaning Code Meaning to set
+     *  @param  schemeVersion The Coding Scheme Designator version to set
+     *  (optional)
+     *  @param  checkValue If OFTrue, VM and VR of values is checked
+     *  @param  autoTag If OFTrue, it is determined automatically if
+     *          tag Code Value, URN Code Value or Long Code Value is used.
+     *          If OFFalse, the classic Code Value is used.
+     *          Default is OFTrue.
+     *  @return EC_Normal if setting was successful, error otherwise
+     */
+    virtual OFCondition set(const OFString& value,
+                            const OFString& scheme,
+                            const OFString& meaning,
+                            const OFString& schemeVersion = "",
+                            const OFBool checkValue       = OFTrue,
+                            const OFBool autoTag          = OFTrue);
+
+    /** Returns string representation reflecting the coded value.
+     *  Mostly useful for debugging purposes.
+     *  @return String representing the coded value
+     */
+    virtual OFString toString();
 
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   *  @param  parent The parent of the IOD component (NULL if none or unknown)
-   */
-  CodeSequenceMacro(OFshared_ptr<DcmItem> item,
-                    OFshared_ptr<IODRules> rules,
-                    IODComponent* parent = NULL);
-
-  /** Constructor
-   *  @param  parent The parent of the IOD component (NULL if none or unknown)
-   */
-  CodeSequenceMacro(IODComponent* parent = NULL);
-
-  /** Copy Constructor, performs deep copy
-   *  @param  rhs The parent of the IOD component (NULL if none or unknown)
-   */
-  CodeSequenceMacro(const CodeSequenceMacro& rhs);
-
-  /** Convenience constructor to set initial values
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   *  @param  parent The parent of the IOD component (NULL if none or unknown)
-   *  @param  codeValue The code value
-   *  @param  codingSchemeDesignator The coding scheme designator
-   *  @param  codeMeaning The code meaning
-   *  @param  codingSchemeVersion The coding scheme version (might be empty if
-   *          coding scheme is unique)
-   */
-  CodeSequenceMacro(OFshared_ptr<DcmItem> item,
-                    OFshared_ptr<IODRules> rules,
-                    IODComponent* parent,
-                    const OFString& codeValue,
-                    const OFString& codingSchemeDesignator,
-                    const OFString& codeMeaning,
-                    const OFString& codingSchemeVersion = "");
-
-  /** Convenience constructor to set initial values
-   *  @param  codeValue The code value
-   *  @param  codingSchemeDesignator The coding scheme designator
-   *  @param  codeMeaning The code meaning
-   *  @param  codingSchemeVersion The coding scheme version (might be empty if
-   *          coding scheme is unique)
-   *  @param  parent The parent of the IOD component (NULL if none or unknown)
-   */
-  CodeSequenceMacro(const OFString& codeValue,
-                    const OFString& codingSchemeDesignator,
-                    const OFString& codeMeaning,
-                    const OFString& codingSchemeVersion = "",
-                    IODComponent* parent = NULL);
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of macro
-   *  @return Name of the component ("CodeSequenceMacro")
-   */
-  virtual OFString getName() const;
-
-  /** Virtual Destructor
-   */
-  virtual ~CodeSequenceMacro();
-
-   /** Get Code Value
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getCodeValue(OFString &value,
-                                   const signed long pos = 0);
-
-   /** Get Coding Scheme Designator
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos   Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getCodingSchemeDesignator(OFString &value,
-                                                const signed long pos = 0);
-
-   /** Get Coding Scheme Version
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return  EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getCodingSchemeVersion(OFString &value,
-                                             const signed long pos = 0);
-
-   /** Get Code Meaning
-    *  @param  value  Reference to variable in which the value should be stored
-    *  @param  pos    Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getCodeMeaning(OFString &value,
-                                     const signed long pos = 0);
-
-  /** Returns whether code is empty, i.e. no component of the Code Sequence Macro
-   *  is set. This can be used in order to find out whether someone actually
-   *  wanted to fill in a valid code as opposed of leaving it unset.
-   *  @return OFTrue if no component of this class is set, OFFalse otherwise.
-   */
-  virtual OFBool empty();
-
-  /** Set Code Value
-   *  @param  value The value to set
-   *  @param  checkValue If OFTrue, VM and VR of value are checked
-   *  @return EC_Normal if setting was successful, error otherwise
-   */
-  virtual OFCondition setCodeValue(const OFString &value,
-                                   const OFBool checkValue = OFTrue);
-
-  /** Set Coding Scheme Designator
-   *  @param  value The value to set
-   *  @param  checkValue If OFTrue, VM and VR of value are checked
-   *  @return EC_Normal if setting was successful, error otherwise
-   */
-  virtual OFCondition setCodingSchemeDesignator(const OFString &value,
-                                                const OFBool checkValue = OFTrue);
-
-  /** Set Coding Scheme Version
-   *  @param  value The value to set
-   *  @param  checkValue If OFTrue, VM and VR of value are checked
-   *  @return EC_Normal if setting was successful, error otherwise
-   */
-  virtual OFCondition setCodingSchemeVersion(const OFString &value,
-                                             const OFBool checkValue = OFTrue);
-
-  /** Set Code Meaning
-   *  @param  value The value to set
-   *  @param  checkValue If OFTrue, VM and VR of value are checked
-   *  @return EC_Normal if setting was successful, error otherwise
-   */
-  virtual OFCondition setCodeMeaning(const OFString &value,
-                                     const OFBool checkValue = OFTrue);
-
-  /** Set all values in this class conveniently
-   *  @param  value Code Value to set
-   *  @param  scheme Coding Scheme Designator to set
-   *  @param  meaning Code Meaning to set
-   *  @param  schemeVersion The Coding Scheme Designator version to set
-   *  (optional)
-   *  @param  checkValue If OFTrue, VM and VR of values is checked
-   *  @return EC_Normal if setting was successful, error otherwise
-   */
-  virtual OFCondition set(const OFString &value,
-                          const OFString &scheme,
-                          const OFString &meaning,
-                          const OFString &schemeVersion = "",
-                          const OFBool checkValue = OFTrue);
-
-  virtual OFString toString();
-
+protected:
+    /** Deletes all out of the the following list of tags:
+     *  Code Value, Long Code Value and URN Code Value
+     *  @param  keepTag The tag to be keep
+     */
+    void deleteUnusedCodeValues(const DcmTagKey& keepTag);
 };
 
-
 /** Code with Modifier(s). Represents the combination of a Code Sequence Macro
  *  that is amended by a Modifier Code Sequence with one or more items. The
  *  VM and requirement type of the Modifier Code Sequence can be configured, as
@@ -217,262 +271,244 @@ class DCMTK_DCMIOD_EXPORT CodeWithModifiers : public CodeSequenceMacro
 {
 
 public:
-
-  /** Constructor
-   *  @param  modifierType Denotes type of Modifier Code Sequence (i.e. 1, 1C,
-   *          2, 2C or 3)
-   *  @param  modifierVM Denotes how many items are allowed in the Modifier Code
-   *          Sequence
-   *  @param  modifierSeq Tag of the sequence that holds the modifier codes.
-   *          The default is the Modifier Code Sequence.
-   */
-  CodeWithModifiers(const OFString& modifierType,
-                    const OFString& modifierVM = "1-n",
-                    const DcmTagKey& modifierSeq = DCM_ModifierCodeSequence);
-
-  /** Copy constructor, performs deep copy.
-   *  @param  rhs The component to be copied from
-   */
-  CodeWithModifiers(const CodeWithModifiers& rhs);
-
-  /** Assignment operator, performs deep copy.
-   *  @param  rhs The component to be assigned from
-   *  @return Reference to this object
-   */
-  CodeWithModifiers& operator=(const CodeWithModifiers& rhs);
-
-  /** Virtual Destructor, frees memory
-   */
-  virtual ~CodeWithModifiers();
-
-  /** Clear all attributes from the data that are handled by this component.
-   *  An attribute is considered belonging to the module if there are rules
-   *  marked as belonging to this module via the rule's module name.
-   */
-  void clearData();
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get rules handled by this module
-   *  @return The rules
-   */
-  OFshared_ptr<IODRules> getRules()
-  {
-    return m_Rules;
-  }
-
-  /** Get name of component
-   *  @return Name of the component
-   */
-  virtual OFString getName() const;
-
-  /** Get modifier code denoted by index
-   *  @param  index Index of modifier code to get (first modifier = 0)
-   *  @return Code if modifier with index exists, NULL otherwise
-   */
-  virtual CodeSequenceMacro* getModifier(const size_t index = 0);
-
-  /** Adds modifier code
-   *  @param  modifier The code to be added
-   *  @return EC_Normal if adding was successful, error otherwise
-   */
-  virtual OFCondition addModifier(const CodeSequenceMacro& modifier);
-
-  /** Read attributes from given item into this class
-   *  @param source  The source to read from
-   *  @param clearOldData If OFTrue, old data is cleared before reading. Otherwise
-   *         old data is overwritten (or amended)
-   *  @result EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write attributes from this class into given item
-   *  @param  destination The item to write to
-   *  @result EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& destination);
-
-  /** Check whether this component's data satisfies the underlying
-   *  rules
-   *  @param  quiet If OFTrue, not error / warning messages will be produced. Only
-   *                the returned error code will indicate error or OK. Per default,
-   *                logging output is produced (OFFalse).
-   *  @result EC_Normal if rules are satisfied, error otherwise
-   */
-  virtual OFCondition check(const OFBool quiet = OFFalse);
-
-  /** Comparison operator for IOD Components
-   *  @param  rhs The right hand side of the comparison
-   *  @return 0, if the given object is equal to this object, other value otherwise
-   */
-  virtual int compare(const IODComponent& rhs) const;
+    /** Constructor
+     *  @param  modifierType Denotes type of Modifier Code Sequence (i.e. 1, 1C,
+     *          2, 2C or 3)
+     *  @param  modifierVM Denotes how many items are allowed in the Modifier Code
+     *          Sequence
+     *  @param  modifierSeq Tag of the sequence that holds the modifier codes.
+     *          The default is the Modifier Code Sequence.
+     */
+    CodeWithModifiers(const OFString& modifierType,
+                      const OFString& modifierVM   = "1-n",
+                      const DcmTagKey& modifierSeq = DCM_ModifierCodeSequence);
+
+    /** Copy constructor, performs deep copy.
+     *  @param  rhs The component to be copied from
+     */
+    CodeWithModifiers(const CodeWithModifiers& rhs);
+
+    /** Assignment operator, performs deep copy.
+     *  @param  rhs The component to be assigned from
+     *  @return Reference to this object
+     */
+    CodeWithModifiers& operator=(const CodeWithModifiers& rhs);
+
+    /** Virtual Destructor, frees memory
+     */
+    virtual ~CodeWithModifiers();
+
+    /** Clear all attributes from the data that are handled by this component.
+     *  An attribute is considered belonging to the module if there are rules
+     *  marked as belonging to this module via the rule's module name.
+     */
+    void clearData();
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get rules handled by this module
+     *  @return The rules
+     */
+    OFshared_ptr<IODRules> getRules()
+    {
+        return m_Rules;
+    }
+
+    /** Get name of component
+     *  @return Name of the component
+     */
+    virtual OFString getName() const;
+
+    /** Get modifier code denoted by index
+     *  @param  index Index of modifier code to get (first modifier = 0)
+     *  @return Code if modifier with index exists, NULL otherwise
+     */
+    virtual CodeSequenceMacro* getModifier(const size_t index = 0);
+
+    /** Adds modifier code
+     *  @param  modifier The code to be added
+     *  @return EC_Normal if adding was successful, error otherwise
+     */
+    virtual OFCondition addModifier(const CodeSequenceMacro& modifier);
+
+    /** Read attributes from given item into this class
+     *  @param source  The source to read from
+     *  @param clearOldData If OFTrue, old data is cleared before reading. Otherwise
+     *         old data is overwritten (or amended)
+     *  @result EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write attributes from this class into given item
+     *  @param  destination The item to write to
+     *  @result EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& destination);
+
+    /** Check whether this component's data satisfies the underlying
+     *  rules
+     *  @param  quiet If OFTrue, not error / warning messages will be produced. Only
+     *                the returned error code will indicate error or OK. Per default,
+     *                logging output is produced (OFFalse).
+     *  @result EC_Normal if rules are satisfied, error otherwise
+     */
+    virtual OFCondition check(const OFBool quiet = OFFalse);
+
+    /** Comparison operator for IOD Components
+     *  @param  rhs The right hand side of the comparison
+     *  @return 0, if the given object is equal to this object, other value otherwise
+     */
+    virtual int compare(const IODComponent& rhs) const;
 
 private:
+    /// Private undefined default constructor
+    CodeWithModifiers();
 
-  /// Private undefined default constructor
-  CodeWithModifiers();
+    /// Items of Modifier Code Sequence
+    OFVector<CodeSequenceMacro*> m_Modifiers;
 
-  /// Items of Modifier Code Sequence
-  OFVector<CodeSequenceMacro*> m_Modifiers;
+    /// Type 1,2,3,1C or 2C
+    OFString m_ModifierType;
 
-  /// Type 1,2,3,1C or 2C
-  OFString m_ModifierType;
+    /// 1, 1-n, 2-2n, ...
+    OFString m_ModifierVM;
 
-  /// 1, 1-n, 2-2n, ...
-  OFString m_ModifierVM;
-
-  /// The sequence tag key that contains the modifier codes
-  DcmTagKey m_CodeModifierSeq;
+    /// The sequence tag key that contains the modifier codes
+    DcmTagKey m_CodeModifierSeq;
 };
 
-
-
 /** Class implementing the SOP Instance Reference Macro
  */
 class DCMTK_DCMIOD_EXPORT SOPInstanceReferenceMacro : public IODComponent
 {
 
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   *  @param  parent The parent of the IOD component (NULL if none or unknown)
-   */
-  SOPInstanceReferenceMacro(OFshared_ptr<DcmItem> item,
-                            OFshared_ptr<IODRules> rules,
-                            IODComponent* parent = NULL);
-
-  /** Constructor
-   *  @param  parent The parent of the IOD component (NULL if none or unknown)
-   */
-  SOPInstanceReferenceMacro(IODComponent* parent = NULL);
-
-  /** Virtual Destructor
-   */
-  virtual ~SOPInstanceReferenceMacro();
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of macro
-   *  @return Name of the module ("SOPInstanceReferenceMacro")
-   */
-  virtual OFString getName() const;
-
-   /** Get Referenced SOP Class UID
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos   Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-   virtual OFCondition getReferencedSOPClassUID(OFString &value,
-                                                const signed long pos = 0);
-   /** Get Referenced SOP Instance UID
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos   Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-   virtual OFCondition getReferencedSOPInstanceUID(OFString &value,
-                                                   const signed long pos = 0);
-  /** Set Referenced SOP Class UID
-   *  @param  value The value to set
-   *  @param  checkValue If OFTrue, the value is checked regarding VM and VR
-   *  @return EC_Normal, if successful, error otherwise
-   */
-  virtual OFCondition setReferencedSOPClassUID(const OFString& value,
-                                               const OFBool checkValue = OFTrue);
-  /** Set Referenced SOP Instance UID
-   *  @param  value The value to set
-   *  @param  checkValue If OFTrue, the value is checked regarding VM and VR
-   *  @return EC_Normal, if successful, error otherwise
-   */
-  virtual OFCondition setReferencedSOPInstanceUID(const OFString& value,
-                                                  const OFBool checkValue = OFTrue);
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     *  @param  parent The parent of the IOD component (NULL if none or unknown)
+     */
+    SOPInstanceReferenceMacro(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules, IODComponent* parent = NULL);
+
+    /** Constructor
+     *  @param  parent The parent of the IOD component (NULL if none or unknown)
+     */
+    SOPInstanceReferenceMacro(IODComponent* parent = NULL);
+
+    /** Virtual Destructor
+     */
+    virtual ~SOPInstanceReferenceMacro();
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of macro
+     *  @return Name of the module ("SOPInstanceReferenceMacro")
+     */
+    virtual OFString getName() const;
+
+    /** Get Referenced SOP Class UID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos   Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getReferencedSOPClassUID(OFString& value, const signed long pos = 0);
+    /** Get Referenced SOP Instance UID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos   Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getReferencedSOPInstanceUID(OFString& value, const signed long pos = 0);
+    /** Set Referenced SOP Class UID
+     *  @param  value The value to set
+     *  @param  checkValue If OFTrue, the value is checked regarding VM and VR
+     *  @return EC_Normal, if successful, error otherwise
+     */
+    virtual OFCondition setReferencedSOPClassUID(const OFString& value, const OFBool checkValue = OFTrue);
+    /** Set Referenced SOP Instance UID
+     *  @param  value The value to set
+     *  @param  checkValue If OFTrue, the value is checked regarding VM and VR
+     *  @return EC_Normal, if successful, error otherwise
+     */
+    virtual OFCondition setReferencedSOPInstanceUID(const OFString& value, const OFBool checkValue = OFTrue);
 };
 
-
 /** Class representing the Series and Instance Reference Macro
  */
 class DCMTK_DCMIOD_EXPORT IODSeriesAndInstanceReferenceMacro : public IODComponent
 {
 
 public:
-
-  // Forward declaration
-  class ReferencedSeriesItem;
-
-  /** Constructor
-   *  @param  data The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   *  @param  parent The parent of the IOD component (NULL if none or unknown)
-   */
-  IODSeriesAndInstanceReferenceMacro(OFshared_ptr<DcmItem> data,
-                                     OFshared_ptr<IODRules> rules,
-                                     IODComponent* parent = NULL);
-
-  /** Constructor
-   *  @param  parent The parent component of this class (if applicable, might
-   *          be NULL)
-   */
-  IODSeriesAndInstanceReferenceMacro(IODComponent* parent = NULL);
-
-  /** Virtual Destructor
-   */
-  virtual ~IODSeriesAndInstanceReferenceMacro();
-
-  /** Read Series and Instance Reference Macro from given item
-   *  @param  source The item to read from
-   *  @param  clearOldData If OFTrue, old data is deleted before
-   *          reading (default)
-   *  @return EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write Series and Instance Reference Macro to given item
-   *  @param  destination The item to write to
-   *  @return EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& destination);
-
-  /** Get name of module ("SeriesAndInstanceReferenceMacro")
-   *  @return Name of the module ("SeriesAndInstanceReferenceMacro")
-   */
-  virtual OFString getName() const;
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Clear (removes) all attributes handled by the modules of this component.
-   *  Rules are not reset.
-   */
-  virtual void clearData();
-
-  /** Return reference to list of Referenced Series items
-   *  @return Reference to list of Reference Series Items
-   */
-  OFVector<ReferencedSeriesItem*>& getReferencedSeriesItems();
+    // Forward declaration
+    class ReferencedSeriesItem;
+
+    /** Constructor
+     *  @param  data The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     *  @param  parent The parent of the IOD component (NULL if none or unknown)
+     */
+    IODSeriesAndInstanceReferenceMacro(OFshared_ptr<DcmItem> data,
+                                       OFshared_ptr<IODRules> rules,
+                                       IODComponent* parent = NULL);
+
+    /** Constructor
+     *  @param  parent The parent component of this class (if applicable, might
+     *          be NULL)
+     */
+    IODSeriesAndInstanceReferenceMacro(IODComponent* parent = NULL);
+
+    /** Virtual Destructor
+     */
+    virtual ~IODSeriesAndInstanceReferenceMacro();
+
+    /** Read Series and Instance Reference Macro from given item
+     *  @param  source The item to read from
+     *  @param  clearOldData If OFTrue, old data is deleted before
+     *          reading (default)
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write Series and Instance Reference Macro to given item
+     *  @param  destination The item to write to
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& destination);
+
+    /** Get name of module ("SeriesAndInstanceReferenceMacro")
+     *  @return Name of the module ("SeriesAndInstanceReferenceMacro")
+     */
+    virtual OFString getName() const;
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Clear (removes) all attributes handled by the modules of this component.
+     *  Rules are not reset.
+     */
+    virtual void clearData();
+
+    /** Return reference to list of Referenced Series items
+     *  @return Reference to list of Reference Series Items
+     */
+    OFVector<ReferencedSeriesItem*>& getReferencedSeriesItems();
 
 private:
+    /// Vector with all items of the Referenced Series Sequence
+    OFVector<ReferencedSeriesItem*> m_ReferencedSeriesItems;
 
-  /// Vector with all items of the Referenced Series Sequence
-  OFVector<ReferencedSeriesItem*> m_ReferencedSeriesItems;
-
-  /// Name of this component ("SeriesAndInstanceReferenceMacro")
-  static const OFString m_ComponentName;
-
+    /// Name of this component ("SeriesAndInstanceReferenceMacro")
+    static const OFString m_ComponentName;
 };
 
-
 /** Class representing Items from the Referenced Series Sequence:
  *
  * [Referenced Series Sequence: (SQ, VM 1-n, Type 1C)]
@@ -485,224 +521,205 @@ class DCMTK_DCMIOD_EXPORT IODSeriesAndInstanceReferenceMacro::ReferencedSeriesIt
 {
 
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   *  @param  parent The parent of the IOD component (NULL if none or unknown)
-   */
-  ReferencedSeriesItem(OFshared_ptr<DcmItem> item,
-                       OFshared_ptr<IODRules> rules,
-                       IODComponent* parent = NULL);
-
-  /** Constructor
-   *  @param  parent The parent component of this class (if applicable, might
-   *          be NULL)
-   */
-  ReferencedSeriesItem(IODComponent* parent = NULL);
-
-  /** Destructor
-   */
-  virtual ~ReferencedSeriesItem();
-
-  /** Clear (removes) all attributes handled by the modules of this component.
-   *  Rules are not reset.
-   */
-  virtual void clearData();
-
-  /** Read Referenced Series Sequence item data from given item
-   *  @param  source The item to read from
-   *  @param  clearOldData If OFTrue, old data is cleared before reading
-   *  @return EC_Normal if data could be read successfully, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write this Referenced Series Sequence item data to given item
-   *  @param  destination The item to write to
-   *  @return EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& destination);
-
-  /** Resets rules to their original values.
-   */
-  virtual void resetRules();
-
-  /** Get name of module ("SeriesAndInstanceReferenceMacro")
-   *  @return Name of the module ("SeriesAndInstanceReferenceMacro")
-   */
-  virtual OFString getName() const;
-
-  /** Get Series Instance UID
-   *  @param  value  Reference to variable in which the value should be stored
-   *  @param  pos    Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getSeriesInstanceUID(OFString &value,
-                                           const signed long pos = 0) const;
-
-  /** Set Series Instance UID
-  *  @param  value Value to be set (single value only) or "" for no value
-  *  @param  checkValue Check 'value' for conformance with VR and VM if enabled
-  *  @return status EC_Normal if successful, an error code otherwise
-  */
-  virtual OFCondition setSeriesInstanceUID(const OFString& value,
-                                           const OFBool checkValue = OFTrue);
-
-  virtual OFCondition addReference(const OFString& sopClassUID,
-                                   const OFString& sopInstanceUID);
-
-  /** Get content of the Referenced Instance Sequence
-   *  @return Reference to the Referenced Instance Sequence content
-  */
-  virtual OFVector<SOPInstanceReferenceMacro*>& getReferencedInstanceItems();
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     *  @param  parent The parent of the IOD component (NULL if none or unknown)
+     */
+    ReferencedSeriesItem(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules, IODComponent* parent = NULL);
+
+    /** Constructor
+     *  @param  parent The parent component of this class (if applicable, might
+     *          be NULL)
+     */
+    ReferencedSeriesItem(IODComponent* parent = NULL);
+
+    /** Destructor
+     */
+    virtual ~ReferencedSeriesItem();
+
+    /** Clear (removes) all attributes handled by the modules of this component.
+     *  Rules are not reset.
+     */
+    virtual void clearData();
+
+    /** Read Referenced Series Sequence item data from given item
+     *  @param  source The item to read from
+     *  @param  clearOldData If OFTrue, old data is cleared before reading
+     *  @return EC_Normal if data could be read successfully, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write this Referenced Series Sequence item data to given item
+     *  @param  destination The item to write to
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& destination);
+
+    /** Resets rules to their original values.
+     */
+    virtual void resetRules();
+
+    /** Get name of module ("SeriesAndInstanceReferenceMacro")
+     *  @return Name of the module ("SeriesAndInstanceReferenceMacro")
+     */
+    virtual OFString getName() const;
+
+    /** Get Series Instance UID
+     *  @param  value  Reference to variable in which the value should be stored
+     *  @param  pos    Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSeriesInstanceUID(OFString& value, const signed long pos = 0) const;
+
+    /** Set Series Instance UID
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR and VM if enabled
+     *  @return status EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSeriesInstanceUID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    virtual OFCondition addReference(const OFString& sopClassUID, const OFString& sopInstanceUID);
+
+    /** Get content of the Referenced Instance Sequence
+     *  @return Reference to the Referenced Instance Sequence content
+     */
+    virtual OFVector<SOPInstanceReferenceMacro*>& getReferencedInstanceItems();
 
 private:
+    /// The name of this component ("SeriesAndInstanceReferenceMacro")
+    static const OFString m_ComponentName;
 
-  /// The name of this component ("SeriesAndInstanceReferenceMacro")
-  static const OFString m_ComponentName;
-
-  /// Vector containing the data of all items of the Referenced Instance Sequence
-  OFVector<SOPInstanceReferenceMacro*> m_ReferencedInstanceSequence;
+    /// Vector containing the data of all items of the Referenced Instance Sequence
+    OFVector<SOPInstanceReferenceMacro*> m_ReferencedInstanceSequence;
 };
 
-
 /** Class representing the Image SOP Instance Reference Macro
  */
 class DCMTK_DCMIOD_EXPORT ImageSOPInstanceReferenceMacro : public SOPInstanceReferenceMacro
 {
 
 public:
-
-  /** Constructor
-   */
-  ImageSOPInstanceReferenceMacro();
-
-  /** Virtual Destructor
-   */
-  virtual ~ImageSOPInstanceReferenceMacro();
-
-  /** Creates an ImageSOPInstanceReferenceMacro object without frame/segment
-   *  reference from required information.
-   *  @param  sopClassUID The SOP Class UID of the reference
-   *  @param  sopInstanceUID The SOP Instance UID of the reference
-   *  @param  result Returns the resulting object if successful, NULL otherwise
-   *  @return EC_Normal if creation was successful, error code otherwise
-   */
-  static OFCondition create(const OFString& sopClassUID,
-                            const OFString& sopInstanceUID,
-                            ImageSOPInstanceReferenceMacro*& result);
-
-  /** Creates an ImageSOPInstanceReferenceMacro object with frame or segment
-   *  references from required information.
-   *  @param  sopClassUID The SOP Class UID of the reference
-   *  @param  sopInstanceUID The SOP Instance UID of the reference
-   *  @param  refFramesOrSegments Reference to specific frames of an image or
-   *          segments of a Segmentation object. The decision (image or
-   *          segmentation) is based on the SOP Class; in case it is the
-   *          Segmentation Storage SOP Class, the parameter is interpreted
-   *          as segment references, otherwise as frame references. If this
-   *          parameter is provided empty, then no frame/segment reference is
-   *          set at all.
-   *  @param  result Returns the resulting object if successful, NULL otherwise
-   *  @return EC_Normal if creation was successful, error code otherwise
-   */
-  static OFCondition create(const OFString& sopClassUID,
-                            const OFString& sopInstanceUID,
-                            const OFVector<Uint16>& refFramesOrSegments,
-                            ImageSOPInstanceReferenceMacro*& result);
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type
-   *  @param  rhs The right hand side of the comparison
-   *  @return 0 If the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the rhs object, or all compared components match
-   *          but the rhs component is shorter. Also returned if rhs cannot be
-   *          casted to DcmAttributeTag.
-   *          1 if either the value of the first component that does not match
-   *          is greater in the rhs object, or all compared components match
-   *          but the rhs component is longer.
-   */
-  virtual int compare(const IODComponent& rhs) const;
-
-  /** Clear data
-   */
-  virtual void clear();
-
-  /** Read Image SOP Instance Reference Macro from given item
-   *  @param  source The item to read from
-   *  @param  clearOldData If OFTrue (default), old data is cleared before reading
-   *  @return EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write Image SOP Instance Reference Macrom to given item
-   *  @param  item The item to write to
-   *  @return EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
-
-   /** Get Referenced Frame Number
-    *  @param  values Reference to variable in which the value should be stored
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getReferencedFrameNumber(OFVector<Uint16> &values);
-
-   /** Get Referenced Segment Number
-    *  @param  values Reference to variable in which the value should be stored
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getReferencedSegmentNumber(OFVector<Uint16> &values);
-
-  /** Set Referenced Frame Number
-   *  @param  values The frame numbers that shoule be referenced
-   *  @param  checkValue  If OFTrue (default) the given values will be checked
-   *  @return EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition setReferencedFrameNumber(const OFVector<Uint16>& values,
-                                               const OFBool checkValue = OFTrue);
-  /** Add a Referenced Frame Number
-   *  @param  value The frame number to add
-   *  @param  checkValue If OFTrue, consistency checks are performed (as possible)
-   *  @return EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition addReferencedFrameNumber(const Uint16& value,
-                                               const OFBool checkValue = OFTrue);
-  /** Set the Referenced Segment Numbers
-   *  @param  values The segment numbers to add
-   *  @param  checkValue  If OFTrue, consistency checks are performed (as possible)
-   *  @return EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition setReferencedSegmentNumber(const OFVector<Uint16>& values,
-                                                 const OFBool checkValue = OFTrue);
-
-  /** Add a Referenced Segment Number
-   *  @param  value The segment number to add
-   *  @param  checkValue If OFTrue, consistency checks are performed (as possible)
-   *  @return EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition addReferencedSegmentNumber(const Uint16& value,
-                                                 const OFBool checkValue = OFTrue);
+    /** Constructor
+     */
+    ImageSOPInstanceReferenceMacro();
+
+    /** Virtual Destructor
+     */
+    virtual ~ImageSOPInstanceReferenceMacro();
+
+    /** Creates an ImageSOPInstanceReferenceMacro object without frame/segment
+     *  reference from required information.
+     *  @param  sopClassUID The SOP Class UID of the reference
+     *  @param  sopInstanceUID The SOP Instance UID of the reference
+     *  @param  result Returns the resulting object if successful, NULL otherwise
+     *  @return EC_Normal if creation was successful, error code otherwise
+     */
+    static OFCondition
+    create(const OFString& sopClassUID, const OFString& sopInstanceUID, ImageSOPInstanceReferenceMacro*& result);
+
+    /** Creates an ImageSOPInstanceReferenceMacro object with frame or segment
+     *  references from required information.
+     *  @param  sopClassUID The SOP Class UID of the reference
+     *  @param  sopInstanceUID The SOP Instance UID of the reference
+     *  @param  refFramesOrSegments Reference to specific frames of an image or
+     *          segments of a Segmentation object. The decision (image or
+     *          segmentation) is based on the SOP Class; in case it is the
+     *          Segmentation Storage SOP Class, the parameter is interpreted
+     *          as segment references, otherwise as frame references. If this
+     *          parameter is provided empty, then no frame/segment reference is
+     *          set at all.
+     *  @param  result Returns the resulting object if successful, NULL otherwise
+     *  @return EC_Normal if creation was successful, error code otherwise
+     */
+    static OFCondition create(const OFString& sopClassUID,
+                              const OFString& sopInstanceUID,
+                              const OFVector<Uint16>& refFramesOrSegments,
+                              ImageSOPInstanceReferenceMacro*& result);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type
+     *  @param  rhs The right hand side of the comparison
+     *  @return 0 If the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the rhs object, or all compared components match
+     *          but the rhs component is shorter. Also returned if rhs cannot be
+     *          casted to DcmAttributeTag.
+     *          1 if either the value of the first component that does not match
+     *          is greater in the rhs object, or all compared components match
+     *          but the rhs component is longer.
+     */
+    virtual int compare(const IODComponent& rhs) const;
+
+    /** Clear data
+     */
+    virtual void clear();
+
+    /** Read Image SOP Instance Reference Macro from given item
+     *  @param  source The item to read from
+     *  @param  clearOldData If OFTrue (default), old data is cleared before reading
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write Image SOP Instance Reference Macrom to given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Get Referenced Frame Number
+     *  @param  values Reference to variable in which the value should be stored
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getReferencedFrameNumber(OFVector<Uint16>& values);
+
+    /** Get Referenced Segment Number
+     *  @param  values Reference to variable in which the value should be stored
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getReferencedSegmentNumber(OFVector<Uint16>& values);
+
+    /** Set Referenced Frame Number
+     *  @param  values The frame numbers that shoule be referenced
+     *  @param  checkValue  If OFTrue (default) the given values will be checked
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition setReferencedFrameNumber(const OFVector<Uint16>& values, const OFBool checkValue = OFTrue);
+    /** Add a Referenced Frame Number
+     *  @param  value The frame number to add
+     *  @param  checkValue If OFTrue, consistency checks are performed (as possible)
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition addReferencedFrameNumber(const Uint16& value, const OFBool checkValue = OFTrue);
+    /** Set the Referenced Segment Numbers
+     *  @param  values The segment numbers to add
+     *  @param  checkValue  If OFTrue, consistency checks are performed (as possible)
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition setReferencedSegmentNumber(const OFVector<Uint16>& values, const OFBool checkValue = OFTrue);
+
+    /** Add a Referenced Segment Number
+     *  @param  value The segment number to add
+     *  @param  checkValue If OFTrue, consistency checks are performed (as possible)
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition addReferencedSegmentNumber(const Uint16& value, const OFBool checkValue = OFTrue);
 
 private:
+    // DICOM attributes.
+    // The comments for each attribute describe "Name: (VR, VM, Type)".
+    // See DICOM standard for further reference.
 
-  // DICOM attributes.
-  // The comments for each attribute describe "Name: (VR, VM, Type)".
-  // See DICOM standard for further reference.
-
-  /// Referenced Frame Number: (IS, 1-n, 1C)
-  DcmIntegerString ReferencedFrameNumber;
-
-  /// Referenced Segment Number: (US, 1-n, 1C)
-  DcmUnsignedShort ReferencedSegmentNumber;
+    /// Referenced Frame Number: (IS, 1-n, 1C)
+    DcmIntegerString ReferencedFrameNumber;
 
+    /// Referenced Segment Number: (US, 1-n, 1C)
+    DcmUnsignedShort ReferencedSegmentNumber;
 };
 
-
 /** Class representing the Primary Anatomic Structure Macro
  */
 typedef CodeWithModifiers PrimaryAnatomicStructureMacro;
@@ -713,584 +730,541 @@ class DCMTK_DCMIOD_EXPORT GeneralAnatomyMacro
 {
 
 public:
-
-  /** Constructor
-   *  @param type Type of Anatomic Region Sequence. Permitted values: If 1,
-   * the class represents the "General Anatomy Mandatory Macro", if
-   * type 2 then it behaves like the "General Anatomy Required Macro",
-   * and type 3 like the "General Anatomy Optional Macro". Other values
-   * are interpreted as type 3 (optional).
-   */
-  GeneralAnatomyMacro(const OFString& type);
-
-  /** Copy constructor, creates deep copy.
-   *  @param  rhs The macro to copy from
-   */
-  GeneralAnatomyMacro(const GeneralAnatomyMacro& rhs);
-
-  /** Virtual destructor
-   */
-  virtual ~GeneralAnatomyMacro();
-
-  /** Clear (removes) all attributes handled by the modules of this component.
-   */
-  virtual void clearData();
-
-  /** Check whether this component's data satisfies the underlying
-   *  rules
-   *  @param  quiet If OFTrue, not error / warning messages will be produced.
-   *          Only the returned error code will indicate error or OK. Per
-   *          default, logging output is produced (OFFalse).
-   *  @result EC_Normal if rules are satisfied, error otherwise
-   */
-  virtual OFCondition check(const OFBool quiet = OFFalse);
-
-  /** Return Anatomic Region
-   *  @return Reference to Anatomic Region Code
-   */
-  virtual CodeSequenceMacro& getAnatomicRegion();
-
-  /** Return Anatomic Region Modifier Codes
-   *  @return Reference to Anatomic Region Modifier codes
-   */
-  virtual OFVector<CodeSequenceMacro*>& getAnatomicRegionModifier();
-
-  /** Return anatomic structure
-   *  @return Reference to anatomic structure macro
-   */
-  virtual PrimaryAnatomicStructureMacro& getPrimaryAnatomicStructure();
-
-  /** Reads Anatomic Region Sequence and Primary Anatomic Structure Macro from
-   *  given item
-   *  @param  source The item to read from
-   *  @param  clearOldData If OFTrue, old data is cleared before reading,
-   *          otherwise it is kept/overwritten.
-   *  @return EC_Normal if no error, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write Anatomic Region Sequence and Primary Anatomic Structure Macro to
-   *  given item
-   *  @param  item The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
-
-  /** Assignment operator (performs deep copy)
-   *  @param  rhs The macro to copy from
-   *  @return Reference to "this" object
-   */
-  GeneralAnatomyMacro& operator=(const GeneralAnatomyMacro &rhs);
-
-  /** Comparison operator that compares the normalized value of this object
-   *  with a given object of the same type, i.e.\ the elements within both
-   *  objects (this and rhs parameter) are compared by value.
-   *  @param  rhs the right hand side of the comparison
-   *  @return 0 if the object values are equal.
-   *          -1 if either the value of the first component that does not match
-   *          is lower in the rhs object, or all compared components match
-   *          but the rhs component is shorter.
-   *          1 if either the value of the first component that does not match
-   *          is greater in the rhs object, or all compared components match
-   *          but the rhs component is longer.
-   */
-  virtual int compare(const GeneralAnatomyMacro& rhs) const;
+    /** Constructor
+     *  @param type Type of Anatomic Region Sequence. Permitted values: If 1,
+     * the class represents the "General Anatomy Mandatory Macro", if
+     * type 2 then it behaves like the "General Anatomy Required Macro",
+     * and type 3 like the "General Anatomy Optional Macro". Other values
+     * are interpreted as type 3 (optional).
+     */
+    GeneralAnatomyMacro(const OFString& type);
+
+    /** Copy constructor, creates deep copy.
+     *  @param  rhs The macro to copy from
+     */
+    GeneralAnatomyMacro(const GeneralAnatomyMacro& rhs);
+
+    /** Virtual destructor
+     */
+    virtual ~GeneralAnatomyMacro();
+
+    /** Clear (removes) all attributes handled by the modules of this component.
+     */
+    virtual void clearData();
+
+    /** Check whether this component's data satisfies the underlying
+     *  rules
+     *  @param  quiet If OFTrue, not error / warning messages will be produced.
+     *          Only the returned error code will indicate error or OK. Per
+     *          default, logging output is produced (OFFalse).
+     *  @result EC_Normal if rules are satisfied, error otherwise
+     */
+    virtual OFCondition check(const OFBool quiet = OFFalse);
+
+    /** Return Anatomic Region
+     *  @return Reference to Anatomic Region Code
+     */
+    virtual CodeSequenceMacro& getAnatomicRegion();
+
+    /** Return Anatomic Region Modifier Codes
+     *  @return Reference to Anatomic Region Modifier codes
+     */
+    virtual OFVector<CodeSequenceMacro*>& getAnatomicRegionModifier();
+
+    /** Return anatomic structure
+     *  @return Reference to anatomic structure macro
+     */
+    virtual PrimaryAnatomicStructureMacro& getPrimaryAnatomicStructure();
+
+    /** Reads Anatomic Region Sequence and Primary Anatomic Structure Macro from
+     *  given item
+     *  @param  source The item to read from
+     *  @param  clearOldData If OFTrue, old data is cleared before reading,
+     *          otherwise it is kept/overwritten.
+     *  @return EC_Normal if no error, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write Anatomic Region Sequence and Primary Anatomic Structure Macro to
+     *  given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Assignment operator (performs deep copy)
+     *  @param  rhs The macro to copy from
+     *  @return Reference to "this" object
+     */
+    GeneralAnatomyMacro& operator=(const GeneralAnatomyMacro& rhs);
+
+    /** Comparison operator that compares the normalized value of this object
+     *  with a given object of the same type, i.e.\ the elements within both
+     *  objects (this and rhs parameter) are compared by value.
+     *  @param  rhs the right hand side of the comparison
+     *  @return 0 if the object values are equal.
+     *          -1 if either the value of the first component that does not match
+     *          is lower in the rhs object, or all compared components match
+     *          but the rhs component is shorter.
+     *          1 if either the value of the first component that does not match
+     *          is greater in the rhs object, or all compared components match
+     *          but the rhs component is longer.
+     */
+    virtual int compare(const GeneralAnatomyMacro& rhs) const;
 
 private:
+    /// Type (1,2,3) of Anatomic Region Sequence.
+    OFString m_Type;
 
-  /// Type (1,2,3) of Anatomic Region Sequence.
-  OFString m_Type;
+    /// Anatomic Region Sequence (SQ, 1, 1) (Code Sequence Macro within item of
+    /// Anatomic Region Sequence))
+    CodeSequenceMacro m_AnatomicRegion;
 
-  /// Anatomic Region Sequence (SQ, 1, 1) (Code Sequence Macro within item of
-  /// Anatomic Region Sequence))
-  CodeSequenceMacro m_AnatomicRegion;
+    /// Anatomic Region Modifier Macro (within item of Anatomic Region Sequence)
+    OFVector<CodeSequenceMacro*> m_AnatomicRegionModifier;
 
-  /// Anatomic Region Modifier Macro (within item of Anatomic Region Sequence)
-  OFVector<CodeSequenceMacro*> m_AnatomicRegionModifier;
-
-  /// Primary Anatomic Structure Macro (on the same level as Anatomic
-  /// Region Sequence)
-  PrimaryAnatomicStructureMacro m_PrimaryAnatomicStructure;
+    /// Primary Anatomic Structure Macro (on the same level as Anatomic
+    /// Region Sequence)
+    PrimaryAnatomicStructureMacro m_PrimaryAnatomicStructure;
 };
 
-
 /** Class representing the Algorithm Identification Macro
  */
 class DCMTK_DCMIOD_EXPORT AlgorithmIdentificationMacro
 {
 
 public:
-
-  /** Constructor
-   */
-  AlgorithmIdentificationMacro();
-
-  /** Virtual destructor
-   */
-  virtual ~AlgorithmIdentificationMacro();
-
-  /** Clear (removes) all attributes handled by the modules of this component.
-   */
-  virtual void clearData();
-
-  /** Perform consistency checks
-   *  @param  quiet If OFTrue, not error / warning messages will be produced.
-   *          Only the returned error code will indicate error or OK. Per
-   *          default, logging output is produced (OFFalse).
-   *  @result EC_Normal if rules are satisfied, error otherwise
-   */
-  virtual OFCondition check(const OFBool quiet = OFFalse);
-
-  /** Return Algorithm Family Code
-   *  @return Reference to algorithm family code
-   */
-  virtual CodeSequenceMacro& getAlgorithmFamilyCode();
-
-  /** Get Algorithm Name Code
-   *  @return Algorithm Name Code
-   */
-  virtual CodeSequenceMacro& getAlgorithmNameCode();
-
-  /** Get Algorithm Name
-   *  @param  value Reference variable to store the value to
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if value could be get, error otherwise
-   */
-  virtual OFCondition getAlgorithmName(OFString& value,
-                                       const signed long pos = 0);
-
-  /** Get Algorithm Version
-   *  @param  value Reference variable to store the value to
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if value could be get, error otherwise
-   */
-  virtual OFCondition getAlgorithmVersion(OFString& value,
-                                          const signed long pos = 0);
-
-  /** Get Algorithm Parameters
-   *  @param  value Reference variable to store the value to
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if value could be get, error otherwise
-   */
-  virtual OFCondition getAlgorithmParameters(OFString& value,
-                                             const signed long pos = 0);
-  /** Get Algorithm Source
-   *  @param  value Reference variable to store the value to
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if value could be get, error otherwise
-   */
-  virtual OFCondition getAlgorithmSource(OFString& value,
-                                         const signed long pos = 0);
-
-  /** Set Algorithm Name
-   *  @param  value The value to be set
-   *  @param  checkValue If OFTrue, the given value is checked
-   *  @return EC_Normal, if value could be set, error otherwise
-   */
-  virtual OFCondition setAlgorithmName(const OFString& value,
-                                       const OFBool checkValue = OFTrue);
-
-  /** Set Algorithm Version
-   *  @param  value The value to be set
-   *  @param  checkValue If OFTrue, the given value is checked
-   *  @return EC_Normal, if value could be set, error otherwise
-   */
-  virtual OFCondition setAlgorithmVersion(const OFString& value,
-                                          const OFBool checkValue = OFTrue);
-
-  /** Set Algorithm Parameters
-   *  @param  value The value to be set
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal, if value could be set, error otherwise
-   */
-  virtual OFCondition setAlgorithmParameters(const OFString& value,
-                                             const OFBool checkValue = OFTrue);
-
-  /** Set Algorithm Source
-   *  @param  value The value to be set
-   *  @param  checkValue If OFTrue, the given value is checked
-   *  @return EC_Normal, if value could be set, error otherwise
-   */
-  virtual OFCondition setAlgorithmSource(const OFString& value,
-                                         const OFBool checkValue = OFTrue);
-
-  /** Reads this macro from given item
-   *  @param  source The item to read from
-   *  @param  clearOldData If OFTrue, old data is cleared before reading,
-   *          otherwise it is kept/overwritten
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write this macro to given item
-   *  @param  item The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
+    /** Constructor
+     */
+    AlgorithmIdentificationMacro();
+
+    /** Virtual destructor
+     */
+    virtual ~AlgorithmIdentificationMacro();
+
+    /** Clear (removes) all attributes handled by the modules of this component.
+     */
+    virtual void clearData();
+
+    /** Perform consistency checks
+     *  @param  quiet If OFTrue, not error / warning messages will be produced.
+     *          Only the returned error code will indicate error or OK. Per
+     *          default, logging output is produced (OFFalse).
+     *  @result EC_Normal if rules are satisfied, error otherwise
+     */
+    virtual OFCondition check(const OFBool quiet = OFFalse);
+
+    /** Return Algorithm Family Code
+     *  @return Reference to algorithm family code
+     */
+    virtual CodeSequenceMacro& getAlgorithmFamilyCode();
+
+    /** Get Algorithm Name Code
+     *  @return Algorithm Name Code
+     */
+    virtual CodeSequenceMacro& getAlgorithmNameCode();
+
+    /** Get Algorithm Name
+     *  @param  value Reference variable to store the value to
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if value could be get, error otherwise
+     */
+    virtual OFCondition getAlgorithmName(OFString& value, const signed long pos = 0);
+
+    /** Get Algorithm Version
+     *  @param  value Reference variable to store the value to
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if value could be get, error otherwise
+     */
+    virtual OFCondition getAlgorithmVersion(OFString& value, const signed long pos = 0);
+
+    /** Get Algorithm Parameters
+     *  @param  value Reference variable to store the value to
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if value could be get, error otherwise
+     */
+    virtual OFCondition getAlgorithmParameters(OFString& value, const signed long pos = 0);
+    /** Get Algorithm Source
+     *  @param  value Reference variable to store the value to
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if value could be get, error otherwise
+     */
+    virtual OFCondition getAlgorithmSource(OFString& value, const signed long pos = 0);
+
+    /** Set Algorithm Name
+     *  @param  value The value to be set
+     *  @param  checkValue If OFTrue, the given value is checked
+     *  @return EC_Normal, if value could be set, error otherwise
+     */
+    virtual OFCondition setAlgorithmName(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Algorithm Version
+     *  @param  value The value to be set
+     *  @param  checkValue If OFTrue, the given value is checked
+     *  @return EC_Normal, if value could be set, error otherwise
+     */
+    virtual OFCondition setAlgorithmVersion(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Algorithm Parameters
+     *  @param  value The value to be set
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal, if value could be set, error otherwise
+     */
+    virtual OFCondition setAlgorithmParameters(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Algorithm Source
+     *  @param  value The value to be set
+     *  @param  checkValue If OFTrue, the given value is checked
+     *  @return EC_Normal, if value could be set, error otherwise
+     */
+    virtual OFCondition setAlgorithmSource(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Reads this macro from given item
+     *  @param  source The item to read from
+     *  @param  clearOldData If OFTrue, old data is cleared before reading,
+     *          otherwise it is kept/overwritten
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write this macro to given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
 
 private:
+    /// Code Sequence Macro from Algorithm Family Code Sequence (single item),
+    /// (SQ, VM 1, Type 1)
+    CodeSequenceMacro m_AlgorithmFamilyCode;
 
-  /// Code Sequence Macro from Algorithm Family Code Sequence (single item),
-  /// (SQ, VM 1, Type 1)
-  CodeSequenceMacro m_AlgorithmFamilyCode;
+    /// Code Sequence Macro from Algorithm Name Code Sequence (single item)
+    /// (SQ, VM 1, Type 3)
+    CodeSequenceMacro m_AlgorithmNameCode;
 
-  /// Code Sequence Macro from Algorithm Name Code Sequence (single item)
-  /// (SQ, VM 1, Type 3)
-  CodeSequenceMacro m_AlgorithmNameCode;
+    /// Algorithm Name: (LO, VM 1, Typ 1)
+    DcmLongString m_AlgorithmName;
 
-  /// Algorithm Name: (LO, VM 1, Typ 1)
-  DcmLongString m_AlgorithmName;
+    /// Algorithm Version: (LO, VM 1, Typ 1)
+    DcmLongString m_AlgorithmVersion;
 
-  /// Algorithm Version: (LO, VM 1, Typ 1)
-  DcmLongString m_AlgorithmVersion;
+    /// Algorithm Parameters: (LT, VM 1, Typ 3)
+    DcmLongText m_AlgorithmParameters;
 
-  /// Algorithm Parameters: (LT, VM 1, Typ 3)
-  DcmLongText m_AlgorithmParameters;
-
-  /// Algorithm Source: (LO, VM 1, Typ 3)
-  DcmLongString m_AlgorithmSource;
+    /// Algorithm Source: (LO, VM 1, Typ 3)
+    DcmLongString m_AlgorithmSource;
 };
 
-
 /** Content Identification Macro
  */
 class DCMTK_DCMIOD_EXPORT ContentIdentificationMacro
 {
 
 public:
-
-  /** Class representing an Alternate Content Description item
-   */
-  class DCMTK_DCMIOD_EXPORT AlternateContentDescriptionItem
-  {
+    /** Class representing an Alternate Content Description item
+     */
+    class DCMTK_DCMIOD_EXPORT AlternateContentDescriptionItem
+    {
     public:
-
-      /** Constructor
-       */
-      AlternateContentDescriptionItem();
-
-      /** Virtual destructor
-       */
-      virtual ~AlternateContentDescriptionItem();
-
-      /** Clear (removes) all attributes handled by the modules of this component.
-       */
-      virtual void clearData();
-
-      /** Get Content Description
-       *  @param  value Reference variable to store the value to
-       *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-       *  @return EC_Normal if successful, error otherwise
-       */
-      virtual OFCondition getContentDescription(OFString& value,
-                                                const signed long pos = 0);
-      /** Get Language Code
-       *  @return Reference to the language code
-       */
-      virtual CodeSequenceMacro& getLanguageCode();
-
-      /** Set Content Description
-       *  @param  value The value to set
-       *  @param  checkValue If OFTrue, consistency check is performed
-       *  @result EC_Normal if setting was successful, error otherwise
-       */
-      virtual OFCondition setContentDescription(const OFString& value,
-                                                const OFBool checkValue = OFTrue);
-
-      /** Read Alternate Content Description Sequence item from given item
-       *  @param  source The item to read from
-       *  @param  clearOldData If OFTrue, old data is cleared before reading,
-       *          otherwise it is kept/overwritten
-       *  @result EC_Normal, if reading was successful, error otherwise
-       */
-      virtual OFCondition read(DcmItem& source,
-                               const OFBool clearOldData = OFTrue);
-
-      /** Write alternate content description item to given item
-       *  @param  item The item to write to
-       *  @result EC_Normal, if writing was successful, error otherwise
-       */
-      virtual OFCondition write(DcmItem& item);
+        /** Constructor
+         */
+        AlternateContentDescriptionItem();
+
+        /** Virtual destructor
+         */
+        virtual ~AlternateContentDescriptionItem();
+
+        /** Clear (removes) all attributes handled by the modules of this component.
+         */
+        virtual void clearData();
+
+        /** Get Content Description
+         *  @param  value Reference variable to store the value to
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal if successful, error otherwise
+         */
+        virtual OFCondition getContentDescription(OFString& value, const signed long pos = 0);
+        /** Get Language Code
+         *  @return Reference to the language code
+         */
+        virtual CodeSequenceMacro& getLanguageCode();
+
+        /** Set Content Description
+         *  @param  value The value to set
+         *  @param  checkValue If OFTrue, consistency check is performed
+         *  @result EC_Normal if setting was successful, error otherwise
+         */
+        virtual OFCondition setContentDescription(const OFString& value, const OFBool checkValue = OFTrue);
+
+        /** Read Alternate Content Description Sequence item from given item
+         *  @param  source The item to read from
+         *  @param  clearOldData If OFTrue, old data is cleared before reading,
+         *          otherwise it is kept/overwritten
+         *  @result EC_Normal, if reading was successful, error otherwise
+         */
+        virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+        /** Write alternate content description item to given item
+         *  @param  item The item to write to
+         *  @result EC_Normal, if writing was successful, error otherwise
+         */
+        virtual OFCondition write(DcmItem& item);
 
     private:
-
-      /// Content Description: (LO, VM 1, Type 1)
-      DcmLongString m_ContentDescription;
-
-      /// Item of Language Code Sequence: (SQ, VM 1, Type 1)
-      CodeSequenceMacro m_LanguageCode;
-  };
-
-  /** Constructor
-   */
-  ContentIdentificationMacro();
-
-  /** Constructor initializing basic data
-   *  @param  instanceNumber Instance Number
-   *  @param  contentLabel Content Label
-   *  @param  contentDescription Content Description, may be empty
-   *  @param  contentCreatorName Content Creator's Name, may be empty
-   */
-  ContentIdentificationMacro(const OFString& instanceNumber,
-                             const OFString& contentLabel,
-                             const OFString& contentDescription,
-                             const OFString& contentCreatorName);
-
-  /** Copy constructor
-   *  @param  rhs The macro to copy from (deep copy)
-   */
-  ContentIdentificationMacro(const ContentIdentificationMacro& rhs);
-
-  /** Create Content Identification Macro with minimally required data.
-   *  @param  instanceNumber Instance Number
-   *  @param  contentLabel Content Label
-   *  @param  contentDescription Content Description, may be empty
-   *  @param  contentCreatorName Content Creator's Name, may be empty
-   *  @param  result Returns created macro if successful, NULL otherwise
-   *  @return EC_Normal if creation was successful, error otherwise
-   */
-  static OFCondition create(const OFString& instanceNumber,
-                            const OFString& contentLabel,
-                            const OFString& contentDescription,
-                            const OFString& contentCreatorName,
-                            ContentIdentificationMacro*& result);
-
-  /** Assignment operator (deep copy)
-   *  @param  rhs The macro to copy from
-   *  @return Reference to "this" object
-   */
-  ContentIdentificationMacro& operator=(const ContentIdentificationMacro& rhs);
-
-  /** Virtual destructor
-   */
-  virtual ~ContentIdentificationMacro();
-
-  /** Get rules for this data structure
-   *  @return Reference to the rules
-   */
-  virtual IODRules& getIODRules();
-
-  /** Clear (removes) all attributes handled by the modules of this component.
-   */
-  virtual void clearData();
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of macro
-   *  @return Name of the module ("ContentIdentificationMacro")
-   */
-  virtual OFString getName() const;
-
-
-  /** Check whether this component's data satisfies the underlying
-   *  rules
-   *  @param  quiet If OFTrue, not error / warning messages will be produced.
-   *                Only the returned error code will indicate error or OK. Per
-   *                default, logging output is produced (OFFalse).
-   *  @result EC_Normal if rules are satisfied, error otherwise
-   */
-  virtual OFCondition check(const OFBool quiet = OFFalse);
-
-  /** Get Instance Number
-   *  @param  value Variable to store the result to
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if value could be get, error otherwise
-   */
-  virtual OFCondition getInstanceNumber(OFString& value,
-                                        const signed long pos = 0) const;
-
-  /** Get Content Label
-   *  @param  value Variable to store the result to
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if value could be get, error otherwise
-   */
-  virtual OFCondition getContentLabel(OFString& value,
-                                      const signed long pos = 0) const;
-
-  /** Get Content Description
-   *  @param  value Variable to store the result to
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if value could be get, error otherwise
-   */
-  virtual OFCondition getContentDescription(OFString& value,
-                                            const signed long pos = 0) const;
-
-  /** Get Alternate Content Description items
-   *  @return Reference to the items
-   */
-  virtual OFVector<AlternateContentDescriptionItem*>& getAlternateContentDescription();
-
-  /** Get Content Creator Name
-   *  @param  value Variable to store the result to
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if value could be get, error otherwise
-   */
-  virtual OFCondition getContentCreatorName(OFString& value,
-                                            const signed long pos = 0) const;
-
-  /** Get Content Creator Identification Code
-   *  @return Reference to code
-   */
-  virtual CodeSequenceMacro& getContentCreatorIdentificationCode();
-
-  /** Set Instance Number
-   *  @param  value Value to be set
-   *  @param  checkValue If OFTrue, value is checked for validity
-   *  @return EC_Normal if setting was successful, error otherwise
-   */
-  virtual OFCondition setInstanceNumber(const OFString& value,
-                                        const OFBool checkValue = OFTrue);
-
-  /** Set Content Label
-   *  @param  value Value to be set
-   *  @param  checkValue If OFTrue, value is checked for validity
-   *  @return EC_Normal if setting was successful, error otherwise
-   */
-  virtual OFCondition setContentLabel(const OFString& value,
-                                      const OFBool checkValue = OFTrue);
-
-  /** Set Content Description
-   *  @param  value Value to be set
-   *  @param  checkValue If OFTrue, value is checked for validity
-   *  @return EC_Normal if setting was successful, error otherwise
-   */
-  virtual OFCondition setContentDescription(const OFString& value,
-                                            const OFBool checkValue = OFTrue);
-
-  /** Set Content Creator Name
-   *  @param  value Value to be set
-   *  @param  checkValue If OFTrue, value is checked for validity
-   *  @return EC_Normal if setting was successful, error otherwise
-   */
-  virtual OFCondition setContentCreatorName(const OFString& value,
-                                            const OFBool checkValue = OFTrue);
-
-  /** Reads Content Identification Macro from given item
-   *  @param  source The item to read from
-   *  @param  clearOldData If OFTrue, old data is cleared before reading, otherwise
-   *          it is kept/overwritten
-   *  @return EC_Normal if reading was successful, an error code otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write Content Identification Macro to given item
-   *  @param  item The item to write to
-   *  @return EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
+        /// Content Description: (LO, VM 1, Type 1)
+        DcmLongString m_ContentDescription;
+
+        /// Item of Language Code Sequence: (SQ, VM 1, Type 1)
+        CodeSequenceMacro m_LanguageCode;
+    };
+
+    /** Constructor
+     */
+    ContentIdentificationMacro();
+
+    /** Constructor initializing basic data
+     *  @param  instanceNumber Instance Number
+     *  @param  contentLabel Content Label
+     *  @param  contentDescription Content Description, may be empty
+     *  @param  contentCreatorName Content Creator's Name, may be empty
+     */
+    ContentIdentificationMacro(const OFString& instanceNumber,
+                               const OFString& contentLabel,
+                               const OFString& contentDescription,
+                               const OFString& contentCreatorName);
+
+    /** Copy constructor
+     *  @param  rhs The macro to copy from (deep copy)
+     */
+    ContentIdentificationMacro(const ContentIdentificationMacro& rhs);
+
+    /** Create Content Identification Macro with minimally required data.
+     *  @param  instanceNumber Instance Number
+     *  @param  contentLabel Content Label
+     *  @param  contentDescription Content Description, may be empty
+     *  @param  contentCreatorName Content Creator's Name, may be empty
+     *  @param  result Returns created macro if successful, NULL otherwise
+     *  @return EC_Normal if creation was successful, error otherwise
+     */
+    static OFCondition create(const OFString& instanceNumber,
+                              const OFString& contentLabel,
+                              const OFString& contentDescription,
+                              const OFString& contentCreatorName,
+                              ContentIdentificationMacro*& result);
+
+    /** Assignment operator (deep copy)
+     *  @param  rhs The macro to copy from
+     *  @return Reference to "this" object
+     */
+    ContentIdentificationMacro& operator=(const ContentIdentificationMacro& rhs);
+
+    /** Virtual destructor
+     */
+    virtual ~ContentIdentificationMacro();
+
+    /** Get rules for this data structure
+     *  @return Reference to the rules
+     */
+    virtual IODRules& getIODRules();
+
+    /** Clear (removes) all attributes handled by the modules of this component.
+     */
+    virtual void clearData();
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of macro
+     *  @return Name of the module ("ContentIdentificationMacro")
+     */
+    virtual OFString getName() const;
+
+    /** Check whether this component's data satisfies the underlying
+     *  rules
+     *  @param  quiet If OFTrue, not error / warning messages will be produced.
+     *                Only the returned error code will indicate error or OK. Per
+     *                default, logging output is produced (OFFalse).
+     *  @result EC_Normal if rules are satisfied, error otherwise
+     */
+    virtual OFCondition check(const OFBool quiet = OFFalse);
+
+    /** Get Instance Number
+     *  @param  value Variable to store the result to
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if value could be get, error otherwise
+     */
+    virtual OFCondition getInstanceNumber(OFString& value, const signed long pos = 0) const;
+
+    /** Get Content Label
+     *  @param  value Variable to store the result to
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if value could be get, error otherwise
+     */
+    virtual OFCondition getContentLabel(OFString& value, const signed long pos = 0) const;
+
+    /** Get Content Description
+     *  @param  value Variable to store the result to
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if value could be get, error otherwise
+     */
+    virtual OFCondition getContentDescription(OFString& value, const signed long pos = 0) const;
+
+    /** Get Alternate Content Description items
+     *  @return Reference to the items
+     */
+    virtual OFVector<AlternateContentDescriptionItem*>& getAlternateContentDescription();
+
+    /** Get Content Creator Name
+     *  @param  value Variable to store the result to
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if value could be get, error otherwise
+     */
+    virtual OFCondition getContentCreatorName(OFString& value, const signed long pos = 0) const;
+
+    /** Get Content Creator Identification Code
+     *  @return Reference to code
+     */
+    virtual CodeSequenceMacro& getContentCreatorIdentificationCode();
+
+    /** Set Instance Number
+     *  @param  value Value to be set
+     *  @param  checkValue If OFTrue, value is checked for validity
+     *  @return EC_Normal if setting was successful, error otherwise
+     */
+    virtual OFCondition setInstanceNumber(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Content Label
+     *  @param  value Value to be set
+     *  @param  checkValue If OFTrue, value is checked for validity
+     *  @return EC_Normal if setting was successful, error otherwise
+     */
+    virtual OFCondition setContentLabel(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Content Description
+     *  @param  value Value to be set
+     *  @param  checkValue If OFTrue, value is checked for validity
+     *  @return EC_Normal if setting was successful, error otherwise
+     */
+    virtual OFCondition setContentDescription(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Content Creator Name
+     *  @param  value Value to be set
+     *  @param  checkValue If OFTrue, value is checked for validity
+     *  @return EC_Normal if setting was successful, error otherwise
+     */
+    virtual OFCondition setContentCreatorName(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Reads Content Identification Macro from given item
+     *  @param  source The item to read from
+     *  @param  clearOldData If OFTrue, old data is cleared before reading, otherwise
+     *          it is kept/overwritten
+     *  @return EC_Normal if reading was successful, an error code otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write Content Identification Macro to given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
 
 private:
+    // Instance Number: (IS, VM 1, Type 1)
+    DcmIntegerString m_InstanceNumber;
 
-  // Instance Number: (IS, VM 1, Type 1)
-  DcmIntegerString m_InstanceNumber;
+    /// Content Label: (CS, VM 1, Type 1)
+    DcmCodeString m_ContentLabel;
 
-  /// Content Label: (CS, VM 1, Type 1)
-  DcmCodeString m_ContentLabel;
+    /// Content Description: (LO, VM 1, Type 1)
+    DcmLongString m_ContentDescription;
 
-  /// Content Description: (LO, VM 1, Type 1)
-  DcmLongString m_ContentDescription;
+    // Alternate Content Description Sequence (VM 1-n, Type 3)
+    OFVector<AlternateContentDescriptionItem*> m_AlternateContentDescription;
 
-  // Alternate Content Description Sequence (VM 1-n, Type 3)
-  OFVector<AlternateContentDescriptionItem*> m_AlternateContentDescription;
+    /// Content Creator's Name: (LO, VM 1, Type 2)
+    DcmPersonName m_ContentCreatorName;
 
-  /// Content Creator's Name: (LO, VM 1, Type 2)
-  DcmPersonName m_ContentCreatorName;
+    /// Content Creator's Identification Code Sequence
+    CodeSequenceMacro m_ContentCreatorIdentificationCode;
 
-  /// Content Creator's Identification Code Sequence
-  CodeSequenceMacro m_ContentCreatorIdentificationCode;
-
-  /// IOD rules for this data structure
-  IODRules m_IODRules;
+    /// IOD rules for this data structure
+    IODRules m_IODRules;
 };
 
-
 /** Class representing the HL7 V2 Hierarchic Designator Macro
  */
 class DCMTK_DCMIOD_EXPORT HL7HierarchicDesignatorMacro : public IODComponent
 {
 
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   *  @param  parent The parent of the IOD component (NULL if none or unknown)
-   */
-  HL7HierarchicDesignatorMacro(OFshared_ptr<DcmItem> item,
-                               OFshared_ptr<IODRules> rules,
-                               IODComponent* parent = NULL);
-
-  /** Constructor
-   *  @param  parent The parent of the IOD component (NULL if none or unknown)
-   */
-  HL7HierarchicDesignatorMacro(IODComponent* parent = NULL);
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of macro
-   *  @return Name of the module ("HL7HierarchicDesignatorMacro")
-   */
-  virtual OFString getName() const;
-
-  /** Get Local Namespace Entity ID
-   *  @param  value Variable to store the result to
-   *  @param  pos The index (0..VM) of the value to get
-   *  @return EC_Normal if value could be get, error otherwise
-   */
-  virtual OFCondition getLocalNamespaceEntityID(OFString& value,
-                                                const signed long pos = 0) const;
-
-  /** Get Universal Entity ID
-   *  @param  value Variable to store the result to
-   *  @param  pos The index (0..VM) of the value to get
-   *  @return EC_Normal if value could be get, error otherwise
-   */
-  virtual OFCondition getUniversalEntityID(OFString& value,
-                                           const signed long pos = 0) const;
-
-  /** Get Universal Entity ID Type
-   *  @param  value Variable to store the result to
-   *  @param  pos The index (0..VM) of the value to get
-   *  @return EC_Normal if value could be get, error otherwise
-   */
-  virtual OFCondition getUniversalEntityIDType(OFString& value,
-                                               const signed long pos = 0) const;
-
-  /** Set Local Namespace Entity ID
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if setting was successful, error otherwise
-   */
-  virtual OFCondition setLocalNamespaceEntityID(const OFString& value,
-                                            const OFBool checkValue = OFTrue);
-
-  /** Set Universal Entity ID
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if setting was successful, error otherwise
-   */
-  virtual OFCondition setUniversalEntityID(const OFString& value,
-                                           const OFBool checkValue = OFTrue);
-
-  /** Set Universal Entity ID Type
-   *  @param  value Value to be set
-   *  @param  checkValue If OFTrue, value is checked for validity
-   *  @return EC_Normal if setting was successful, error otherwise
-   */
-  virtual OFCondition setUniversalEntityIDType(const OFString& value,
-                                               const OFBool checkValue = OFTrue);
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     *  @param  parent The parent of the IOD component (NULL if none or unknown)
+     */
+    HL7HierarchicDesignatorMacro(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules, IODComponent* parent = NULL);
+
+    /** Constructor
+     *  @param  parent The parent of the IOD component (NULL if none or unknown)
+     */
+    HL7HierarchicDesignatorMacro(IODComponent* parent = NULL);
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of macro
+     *  @return Name of the module ("HL7HierarchicDesignatorMacro")
+     */
+    virtual OFString getName() const;
+
+    /** Get Local Namespace Entity ID
+     *  @param  value Variable to store the result to
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if value could be get, error otherwise
+     */
+    virtual OFCondition getLocalNamespaceEntityID(OFString& value, const signed long pos = 0) const;
+
+    /** Get Universal Entity ID
+     *  @param  value Variable to store the result to
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if value could be get, error otherwise
+     */
+    virtual OFCondition getUniversalEntityID(OFString& value, const signed long pos = 0) const;
+
+    /** Get Universal Entity ID Type
+     *  @param  value Variable to store the result to
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if value could be get, error otherwise
+     */
+    virtual OFCondition getUniversalEntityIDType(OFString& value, const signed long pos = 0) const;
+
+    /** Set Local Namespace Entity ID
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if setting was successful, error otherwise
+     */
+    virtual OFCondition setLocalNamespaceEntityID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Universal Entity ID
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if setting was successful, error otherwise
+     */
+    virtual OFCondition setUniversalEntityID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Universal Entity ID Type
+     *  @param  value Value to be set
+     *  @param  checkValue If OFTrue, value is checked for validity
+     *  @return EC_Normal if setting was successful, error otherwise
+     */
+    virtual OFCondition setUniversalEntityIDType(const OFString& value, const OFBool checkValue = OFTrue);
 };
 
 /** Class representing the Mandatory View and Slice Progression Direction Macro
@@ -1300,69 +1274,65 @@ class DCMTK_DCMIOD_EXPORT MandatoryViewAndSliceProgressionDirectionMacro : publi
 {
 
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *  class creates an empty data container.
-   *  @param  rules The rule set where this classes rules are added to. If NULL,
-   *          the class creates an empty rule set.
-   *  @param  parent The parent of the IOD component (NULL if none or unknown)
-   */
-  MandatoryViewAndSliceProgressionDirectionMacro(OFshared_ptr<DcmItem> item,
-                                                 OFshared_ptr<IODRules> rules,
-                                                 IODComponent* parent = NULL);
-
-  /** Constructor
-   *  @param  parent The parent of the IOD component (NULL if none or unknown)
-   */
-  MandatoryViewAndSliceProgressionDirectionMacro(IODComponent* parent = NULL);
-
-  /** Clear (removes) all attributes handled by the modules of this component.
-   */
-  virtual void clearData();
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of macro
-   *  @return Name of the module ("MandatoryViewAndSliceProgressionDirectionMacro")
-   */
-  virtual OFString getName() const;
-
-  /** Read Mandatory View and Slice Progression Direction Macro from given item
-   *  @param  source The item to read from
-   *  @param  clearOldData If OFTrue (default), old data is cleared
-   *  before reading
-   *  @return EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write Mandatory View and Slice Progression Direction Macro to given item
-   *  @param  item The item to write to
-   *  @return EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
-
-  /** Get View Code
-   *  @return Reference to code
-   */
-  virtual CodeSequenceMacro& getViewCode();
-
-  /** Get View Modifier Code
-   *  @return Reference to code
-   */
-  virtual OFVector<CodeSequenceMacro*>& getViewModifierCode();
-
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *  class creates an empty data container.
+     *  @param  rules The rule set where this classes rules are added to. If NULL,
+     *          the class creates an empty rule set.
+     *  @param  parent The parent of the IOD component (NULL if none or unknown)
+     */
+    MandatoryViewAndSliceProgressionDirectionMacro(OFshared_ptr<DcmItem> item,
+                                                   OFshared_ptr<IODRules> rules,
+                                                   IODComponent* parent = NULL);
+
+    /** Constructor
+     *  @param  parent The parent of the IOD component (NULL if none or unknown)
+     */
+    MandatoryViewAndSliceProgressionDirectionMacro(IODComponent* parent = NULL);
+
+    /** Clear (removes) all attributes handled by the modules of this component.
+     */
+    virtual void clearData();
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of macro
+     *  @return Name of the module ("MandatoryViewAndSliceProgressionDirectionMacro")
+     */
+    virtual OFString getName() const;
+
+    /** Read Mandatory View and Slice Progression Direction Macro from given item
+     *  @param  source The item to read from
+     *  @param  clearOldData If OFTrue (default), old data is cleared
+     *  before reading
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write Mandatory View and Slice Progression Direction Macro to given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
+
+    /** Get View Code
+     *  @return Reference to code
+     */
+    virtual CodeSequenceMacro& getViewCode();
+
+    /** Get View Modifier Code
+     *  @return Reference to code
+     */
+    virtual OFVector<CodeSequenceMacro*>& getViewModifierCode();
 
 protected:
+    /// View Code Sequence (SQ, VM 1, type 1)
+    CodeSequenceMacro m_ViewCodeSequence;
 
-  /// View Code Sequence (SQ, VM 1, type 1)
-  CodeSequenceMacro m_ViewCodeSequence;
-
-  /// View Modifier Code Sequence (SQ, VM 1-n, type 2C)
-  OFVector<CodeSequenceMacro*> m_ViewModifierCode;
+    /// View Modifier Code Sequence (SQ, VM 1-n, type 2C)
+    OFVector<CodeSequenceMacro*> m_ViewModifierCode;
 };
 
 #endif // IODMACRO_H
index 5d037e2f5728bcbe7b4eedbac31a896c3af63ecb..abc7ffd73a40837dabed2016d42a3e14fa7413f3 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -23,8 +23,9 @@
 #define IODREFERENCES_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/oflog/oflog.h"
 #include "dcmtk/dcmiod/ioddef.h"
+#include "dcmtk/ofstd/ofcond.h"
+#include "dcmtk/ofstd/ofvector.h"
 
 // Forward declaration
 class DcmItem;
@@ -42,30 +43,30 @@ class DcmItem;
  */
 class DCMTK_DCMIOD_EXPORT IODReference
 {
-  public:
+public:
     /// The maximum DICOM entity level that this reference refers to. This is
     /// mostly used in order to check whether a reference is complete or not.
     enum MAX_LEVEL
     {
-      /// Instance Level
-      LEVEL_INSTANCE,
-      /// Series Level
-      LEVEL_SERIES,
-      /// Study level
-      LEVEL_STUDY,
-      /// Patient level
-      LEVEL_PATIENT
+        /// Instance Level
+        LEVEL_INSTANCE,
+        /// Series Level
+        LEVEL_SERIES,
+        /// Study level
+        LEVEL_STUDY,
+        /// Patient level
+        LEVEL_PATIENT
     };
 
     /// Type of reference
     enum TYPE
     {
-      /// Generic (or unknown)
-      GENERIC,
-      /// Reference to an image object, see also class IODImageReference
-      IMAGE,
-      /// Reference to a segmentation object, see also class IDOSegmentationReference
-      SEGMENT
+        /// Generic (or unknown)
+        GENERIC,
+        /// Reference to an image object, see also class IODImageReference
+        IMAGE,
+        /// Reference to a segmentation object, see also class IDOSegmentationReference
+        SEGMENT
     };
 
     /** Constructor, creates empty reference, default level is "STUDY"
@@ -89,7 +90,10 @@ class DCMTK_DCMIOD_EXPORT IODReference
     /** Get type of reference. Base class always returns "GENERIC"
      *  @return Returns "GENERIC" type
      */
-    virtual TYPE getType() const {return GENERIC; }
+    virtual TYPE getType() const
+    {
+        return GENERIC;
+    }
 
     /** Check whether this reference is valid, i.e. complete related to its
      *  level. Also in case of UIDs it is checked whether they conform to the
@@ -142,14 +146,12 @@ class DCMTK_DCMIOD_EXPORT IODReference
     MAX_LEVEL m_Level;
 };
 
-
 /** Class representing a reference to an image. Compared to IODReference, this
  *  class also allows to provide references to specific frames
  */
 class DCMTK_DCMIOD_EXPORT IODImageReference : public IODReference
 {
-  public:
-
+public:
     /** Default constructor, uses level STUDY
      */
     IODImageReference();
@@ -195,7 +197,10 @@ class DCMTK_DCMIOD_EXPORT IODImageReference : public IODReference
     /** Get type (always returns IMAGE type)
      *  @return Returns IMAGE type
      */
-    virtual TYPE getType() const {return IMAGE; }
+    virtual TYPE getType() const
+    {
+        return IMAGE;
+    }
 
     // Avoid overridden virtual function warning, i.e. tell the compiler that
     // we want to have both functions to be polymorph and available to the user.
@@ -208,11 +213,12 @@ class DCMTK_DCMIOD_EXPORT IODImageReference : public IODReference
      *           such frames. First frame is denoted by 1.
      *  @return OFTrue if initialization was successful, OFFalse otherwise
      */
-    virtual OFBool readFromFile(const OFString& filename,
-                                const OFVector<Uint32> frameNumbers);
+    virtual OFBool readFromFile(const OFString& filename, const OFVector<Uint32> frameNumbers);
     /** Destructor
      */
-    virtual ~IODImageReference() {}
+    virtual ~IODImageReference()
+    {
+    }
 
     /** Clear reference data
      */
@@ -222,15 +228,13 @@ class DCMTK_DCMIOD_EXPORT IODImageReference : public IODReference
     OFVector<Uint32> m_ReferencedFrameNumber;
 };
 
-
 /** Class representing a reference to a Segmentation. Compared to IODReference,
  *  this class also allows to provide references to specific segments by
  *  referencing the value of their Segment Number attribute.
  */
 class DCMTK_DCMIOD_EXPORT IODSegmentationReference : public IODReference
 {
-  public:
-
+public:
     /** Constructor allowing to set reference level.
      *  @param  level The maximum level this reference should deal with
      */
@@ -248,7 +252,10 @@ class DCMTK_DCMIOD_EXPORT IODSegmentationReference : public IODReference
     /** Get type (always returns SEGMENT type)
      *  @return Returns SEGMENT type
      */
-    virtual TYPE getType() const {return SEGMENT; }
+    virtual TYPE getType() const
+    {
+        return SEGMENT;
+    }
 
     // Avoid overridden virtual function warning, i.e. tell the compiler that
     // we want to have both functions to be polymorph and available to the user.
@@ -261,12 +268,13 @@ class DCMTK_DCMIOD_EXPORT IODSegmentationReference : public IODReference
      *          contains such Segment Numbers. First segment is 1.
      *  @return OFTrue if initialization was successful, OFFalse otherwise
      */
-    virtual OFBool readFromFile(const OFString& filename,
-                                const OFVector<Uint16> segmentNumbers);
+    virtual OFBool readFromFile(const OFString& filename, const OFVector<Uint16> segmentNumbers);
 
     /** Destructor
      */
-    virtual ~IODSegmentationReference() {}
+    virtual ~IODSegmentationReference()
+    {
+    }
 
     /** Clear reference data
      */
@@ -276,15 +284,13 @@ class DCMTK_DCMIOD_EXPORT IODSegmentationReference : public IODReference
     OFVector<Uint16> m_ReferencedSegmentNumber;
 };
 
-
 /** Class that holds a set of IODReference instances (or its sub classes) and
  *  offers helper functionality to read and write such references
  */
 class DCMTK_DCMIOD_EXPORT IODReferences
 {
 
-  public:
-
+public:
     /** Default constructor
      */
     IODReferences();
@@ -295,6 +301,8 @@ class DCMTK_DCMIOD_EXPORT IODReferences
     IODReferences(const IODReferences& rhs);
 
     /** Assignment operator, copies all provided references
+     *  @param  rhs The right hand side of the assignment
+     *  @return Reference to "this" object
      */
     IODReferences& operator=(const IODReferences& rhs);
 
@@ -354,11 +362,9 @@ class DCMTK_DCMIOD_EXPORT IODReferences
      */
     virtual void clearData();
 
-  private:
-
+private:
     /// Set of references managed by this class
     OFVector<IODReference*> m_References;
 };
 
-
 #endif // IODREFERENCES_H
index 0babf72a15fd132dd0c0a85fd3efc73ba4972964..69697bcd3d0d035189c542781aed31c18451351f 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define IODRULES_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofstring.h"
-#include "dcmtk/ofstd/ofmap.h"
-#include "dcmtk/ofstd/ofcond.h"
 #include "dcmtk/dcmdata/dctagkey.h"
 #include "dcmtk/dcmiod/iodtypes.h"
+#include "dcmtk/ofstd/ofcond.h"
+#include "dcmtk/ofstd/ofmap.h"
+#include "dcmtk/ofstd/ofstring.h"
 
-#define INCLUDE_OSTREAM  // for debugging
+#define INCLUDE_OSTREAM // for debugging
 #include "dcmtk/ofstd/ofstdinc.h"
 
-
 class DcmItem;
 class DcmTagKey;
 class DcmElement;
 class IODRule;
 
-
 /** Class representing rules for a set of DICOM attributes, e.g.\ for
  *  all attributes of a module, macro or the like. At the moment
  *  attributes within sequences are not yet supported.
@@ -47,80 +45,76 @@ class DCMTK_DCMIOD_EXPORT IODRules
 {
 
 public:
-
-  /// iterator type to iterate over rule set
-  typedef OFMap<DcmTagKey, IODRule*>::iterator iterator;
-
-  /// const iterator type to iterate over rule set
-  typedef OFMap<DcmTagKey, IODRule*>::const_iterator const_iterator;
-
-  /** Constructor
-   */
-  IODRules();
-
-  /** Returns deep copy of this object
-   *  @return Deep copy of "this" object
-   */
-  IODRules* clone();
-
-  /** Return iterator to first rule
-   *  @return Iterator to the first rule
-   */
-  iterator begin();
-
-  /** Return iterator to last rule
-   *  @return Iterator to the last rule
-   */
-  iterator end();
-
-  /** Adds rule to this rule set
-   *  @param  rule The rule to add (ownership is transferred to this class)
-   *  @param  overwriteExisting If OFTrue (default), an existing rule for the
-   *          same attribute (tag) is overwritten, otherwise the rule is not
-   *          taken over (and ownership stays with caller)
-   *  @return OFTrue if rule could be added, error otherwise
-   */
-  virtual OFBool addRule(IODRule* rule,
-                         const OFBool overwriteExisting = OFFalse);
-
-  /** Delete rule by given tag key
-   *  @param  key Tag of the attribute rule to be deleted
-   *  @return OFTrue if a rule could be found and deleted, OFFalse otherwise
-   */
-  virtual OFBool deleteRule(const DcmTagKey key);
-
-  /** Get all rules that are marked belonging to a specific module
-   *  @param  moduleName The module name (e.g.\ "PatientModule")
-   *  @return Vector with pointers to all the rules belonging to given module
-   */
-  const OFVector<IODRule*> getByModule(const OFString& moduleName);
-
-  /** Get a rule by its tag
-   *  @param  key The tag to find the rule for
-   *  @return The rule, if found, NULL otherwise
-   */
-  IODRule* getByTag(const DcmTagKey& key) const;
-
-  /** Clear all rules
-   */
-  virtual void clear();
-
-  /** Dump rules to stream, useful for debugging
-   *  @param  out The stream to dump to
-   */
-  virtual void dump(STD_NAMESPACE ostream &out);
-
-  /** Destructor
-   */
-  virtual ~IODRules();
+    /// iterator type to iterate over rule set
+    typedef OFMap<DcmTagKey, IODRule*>::iterator iterator;
+
+    /// const iterator type to iterate over rule set
+    typedef OFMap<DcmTagKey, IODRule*>::const_iterator const_iterator;
+
+    /** Constructor
+     */
+    IODRules();
+
+    /** Returns deep copy of this object
+     *  @return Deep copy of "this" object
+     */
+    IODRules* clone();
+
+    /** Return iterator to first rule
+     *  @return Iterator to the first rule
+     */
+    iterator begin();
+
+    /** Return iterator to last rule
+     *  @return Iterator to the last rule
+     */
+    iterator end();
+
+    /** Adds rule to this rule set
+     *  @param  rule The rule to add (ownership is transferred to this class)
+     *  @param  overwriteExisting If OFTrue (default), an existing rule for the
+     *          same attribute (tag) is overwritten, otherwise the rule is not
+     *          taken over (and ownership stays with caller)
+     *  @return OFTrue if rule could be added, error otherwise
+     */
+    virtual OFBool addRule(IODRule* rule, const OFBool overwriteExisting = OFFalse);
+
+    /** Delete rule by given tag key
+     *  @param  key Tag of the attribute rule to be deleted
+     *  @return OFTrue if a rule could be found and deleted, OFFalse otherwise
+     */
+    virtual OFBool deleteRule(const DcmTagKey key);
+
+    /** Get all rules that are marked belonging to a specific module
+     *  @param  moduleName The module name (e.g.\ "PatientModule")
+     *  @return Vector with pointers to all the rules belonging to given module
+     */
+    const OFVector<IODRule*> getByModule(const OFString& moduleName);
+
+    /** Get a rule by its tag
+     *  @param  key The tag to find the rule for
+     *  @return The rule, if found, NULL otherwise
+     */
+    IODRule* getByTag(const DcmTagKey& key) const;
+
+    /** Clear all rules
+     */
+    virtual void clear();
+
+    /** Dump rules to stream, useful for debugging
+     *  @param  out The stream to dump to
+     */
+    virtual void dump(STD_NAMESPACE ostream& out);
+
+    /** Destructor
+     */
+    virtual ~IODRules();
 
 private:
-
-  /// Map that holds all rules, accessible by their tag key
-  OFMap<DcmTagKey, IODRule*> m_Rules;
+    /// Map that holds all rules, accessible by their tag key
+    OFMap<DcmTagKey, IODRule*> m_Rules;
 };
 
-
 /** Class representing a single rule, that refers to a single attribute.
  *  Each rule is uniquely identified by the attribute's tag key and includes
  *  information on the Value Multiplicity (VM) of the attribute, its type
@@ -133,125 +127,124 @@ private:
 class DCMTK_DCMIOD_EXPORT IODRule
 {
 public:
-
-  /** Constructor to create a new attribute rule
-   *  @param  key The tag key of the attribute
-   *  @param  VM  The VM of the attribute (notation like in DICOM part 6,
-   *          e.g.\ "1-n"), for sequences the number of items allowed.
-   *  @param  type The "IOD type" of the attribute.
-   *          Allowed values "1", "1C", "2", "2C" and "3"
-   *  @param  module The module or "component" this attribute belongs to
-   *  @param  ie The Information Entity the module belongs to
-   *  @param  defaultValue The default value (default: empty)
-   *  @param  privateCreator The private creator of the attribute if attribute
-   *          (default: No private creator)
-   */
-  IODRule(const DcmTagKey& key,
-          const OFString& VM,
-          const OFString& type,
-          const OFString& module,
-          const DcmIODTypes::IOD_IE ie,
-          const OFString& defaultValue = "",
-          const OFString& privateCreator = "");
-
-  /** Return deep copy of this object
-   *  @return Deep copy of "this" object
-   */
-  IODRule* clone();
-
-  /** Get tag key of the attribute rule
-   *  @return The tag key of the rule
-   */
-  virtual DcmTagKey getTagKey() const;
-
-  /** Get private creator of the related attribute
-   *  @return The private creator of the attribute
-   */
-  virtual OFString getPrivateCreator() const;
-
-  /** The requirement type of the attribute (1, 1C, 2, 2C or 3)
-   *  @return The requirement type of the attribute
-   */
-  virtual OFString getType() const;
-
-  /** The VM of the attribute as noted in the DICOM standard part 6,
-   *  e.g.\ "1-n" or "2". For Sequences (VR SQ) whose VM is always 1 by the
-   *  standard, this denotes the number of items permitted.
-   *  @return The VM (or number of items permitted)
-   */
-  virtual OFString getVM() const;
-
-  /** Get module (or component name) the related attribute belongs to
-   *  @return The module or component name (e.g.\ "PatientModule" or
-   *          "CodeSequenceMacro")
-   */
-  virtual OFString getModule() const;
-
-  /** Get default value of this attribute
-   *  @return The default value (might be empty)
-   */
-  virtual OFString getDefaultValue() const;
-
-  /** Get Information Entity the related attribute belongs to
-   *  @return The Information Entity (might be empty)
-   */
-  virtual DcmIODTypes::IOD_IE getIE() const;
-
-  virtual OFBool setPrivateCreator(const OFString& val);
-
-  virtual OFBool setType(const OFString& val);
-
-  virtual OFBool setVM(const OFString& val);
-
-  virtual OFBool setModule(const OFString& val);
-
-  virtual OFBool setDefaultValue(const OFString& val);
-
-  /** Check whether the given item fulfills the requirements of
-   *  this rule, i.e.\ the related attribute is checked within the
-   *  given item
-   *  @param  item The item to check the attribute in
-   *  @param  quiet If OFTrue, no error or warning messages will be produced
-   *          but only the return code will indicate OK or error.
-   *  @return EC_Normal if this rule is fulfilled, error otherwise
-   */
-  virtual OFCondition check(DcmItem& item,
-                            const OFBool quiet = OFFalse);
-
-  /** Virtual Destructor
-   */
-  virtual ~IODRule();
+    /** Constructor to create a new attribute rule
+     *  @param  key The tag key of the attribute
+     *  @param  VM  The VM of the attribute (notation like in DICOM part 6,
+     *          e.g.\ "1-n"), for sequences the number of items allowed.
+     *  @param  type The "IOD type" of the attribute.
+     *          Allowed values "1", "1C", "2", "2C" and "3"
+     *  @param  module The module or "component" this attribute belongs to
+     *  @param  ie The Information Entity the module belongs to
+     *  @param  defaultValue The default value (default: empty)
+     *  @param  privateCreator The private creator of the attribute if attribute
+     *          (default: No private creator)
+     */
+    IODRule(const DcmTagKey& key,
+            const OFString& VM,
+            const OFString& type,
+            const OFString& module,
+            const DcmIODTypes::IOD_IE ie,
+            const OFString& defaultValue   = "",
+            const OFString& privateCreator = "");
+
+    /** Return deep copy of this object
+     *  @return Deep copy of "this" object
+     */
+    IODRule* clone();
+
+    /** Get tag key of the attribute rule
+     *  @return The tag key of the rule
+     */
+    virtual DcmTagKey getTagKey() const;
+
+    /** Get private creator of the related attribute
+     *  @return The private creator of the attribute
+     */
+    virtual OFString getPrivateCreator() const;
+
+    /** The requirement type of the attribute (1, 1C, 2, 2C or 3)
+     *  @return The requirement type of the attribute
+     */
+    virtual OFString getType() const;
+
+    /** The VM of the attribute as noted in the DICOM standard part 6,
+     *  e.g.\ "1-n" or "2". For Sequences (VR SQ) whose VM is always 1 by the
+     *  standard, this denotes the number of items permitted.
+     *  @return The VM (or number of items permitted)
+     */
+    virtual OFString getVM() const;
+
+    /** Get module (or component name) the related attribute belongs to
+     *  @return The module or component name (e.g.\ "PatientModule" or
+     *          "CodeSequenceMacro")
+     */
+    virtual OFString getModule() const;
+
+    /** Get default value of this attribute
+     *  @return The default value (might be empty)
+     */
+    virtual OFString getDefaultValue() const;
+
+    /** Get Information Entity the related attribute belongs to
+     *  @return The Information Entity (might be empty)
+     */
+    virtual DcmIODTypes::IOD_IE getIE() const;
+
+    virtual OFBool setPrivateCreator(const OFString& val);
+
+    virtual OFBool setType(const OFString& val);
+
+    virtual OFBool setVM(const OFString& val);
+
+    virtual OFBool setModule(const OFString& val);
+
+    virtual OFBool setDefaultValue(const OFString& val);
+
+    /** Check whether the given item fulfills the requirements of
+     *  this rule, i.e.\ the related attribute is checked within the
+     *  given item
+     *  @param  item The item to check the attribute in
+     *  @param  quiet If OFTrue, no error or warning messages will be produced
+     *          but only the return code will indicate OK or error.
+     *  @return EC_Normal if this rule is fulfilled, error otherwise
+     */
+    virtual OFCondition check(DcmItem& item, const OFBool quiet = OFFalse);
+
+    /** Virtual Destructor
+     */
+    virtual ~IODRule();
 
 private:
+    /// Private undefined default constructor
+    IODRule();
 
-  /// Private undefined default constructor
-  IODRule();
-
-  /// Private undefined copy constructor
-  IODRule(const IODRule& rhs);
+    /** Private undefined copy constructor
+     *  @param  rhs Right hand side of assignment
+     */
+    IODRule(const IODRule& rhs);
 
-  /// Tag key
-  DcmTagKey m_Key;
+    /// Tag key
+    DcmTagKey m_Key;
 
-  /// VM, see DcmElement::checkVM() for permitted values (e.g.\ "1-n")
-  OFString m_VM;
+    /// VM, see DcmElement::checkVM() for permitted values (e.g.\ "1-n")
+    OFString m_VM;
 
-  /// Requirement type: 1, 1C, 2, 2C or 3
-  OFString m_Type;
+    /// Requirement type: 1, 1C, 2, 2C or 3
+    OFString m_Type;
 
-  /// Module (e.g.\ "PatientModule" or "component name", e.g.\ "CodeSequenceMacro"
-  OFString m_Module;
+    /// Module (e.g.\ "PatientModule" or "component name", e.g.\ "CodeSequenceMacro"
+    OFString m_Module;
 
-  /// The Information Entity the related attribute belongs to according to the
-  /// DICOM Model of the Real World, e.g.\ "Patient" for the attribute
-  /// "Patient Name"
-  DcmIODTypes::IOD_IE m_IE;
+    /// The Information Entity the related attribute belongs to according to the
+    /// DICOM Model of the Real World, e.g.\ "Patient" for the attribute
+    /// "Patient Name"
+    DcmIODTypes::IOD_IE m_IE;
 
-  /// Default value for attribute
-  OFString m_DefaultValue;
+    /// Default value for attribute
+    OFString m_DefaultValue;
 
-  /// Private Creator (if private attribute)
-  OFString m_PrivateCreator;
+    /// Private Creator (if private attribute)
+    OFString m_PrivateCreator;
 };
 
 #endif // IODRULES_H
index d282ace9129e2a26e3ad72eacd6d6d3be4f79ad5..e66e01ef637f0b45b7279ef4547c8f746c10924a 100644 (file)
 #define IODTYPES_H
 
 #include "dcmtk/config/osconfig.h"
+#include "dcmtk/dcmiod/ioddef.h"
 #include "dcmtk/oflog/oflog.h"
 #include "dcmtk/ofstd/ofcond.h"
-#include "dcmtk/dcmiod/ioddef.h"
-#include "dcmtk/dcmiod/cielabutil.h"
 
 // ----------------------------------------------------------------------------
 // Define the loggers for this module
@@ -36,30 +35,28 @@ extern DCMTK_DCMIOD_EXPORT OFLogger DCM_dcmiodLogger;
 
 #define DCMIOD_TRACE(msg) OFLOG_TRACE(DCM_dcmiodLogger, msg)
 #define DCMIOD_DEBUG(msg) OFLOG_DEBUG(DCM_dcmiodLogger, msg)
-#define DCMIOD_INFO(msg)  OFLOG_INFO(DCM_dcmiodLogger, msg)
-#define DCMIOD_WARN(msg)  OFLOG_WARN(DCM_dcmiodLogger, msg)
+#define DCMIOD_INFO(msg) OFLOG_INFO(DCM_dcmiodLogger, msg)
+#define DCMIOD_WARN(msg) OFLOG_WARN(DCM_dcmiodLogger, msg)
 #define DCMIOD_ERROR(msg) OFLOG_ERROR(DCM_dcmiodLogger, msg)
 #define DCMIOD_FATAL(msg) OFLOG_FATAL(DCM_dcmiodLogger, msg)
 
-
 // ----------------------------------------------------------------------------
 // Error constants
 // ----------------------------------------------------------------------------
 
-extern DCMTK_DCMIOD_EXPORT   const OFConditionConst     IOD_EC_WrongSOPClass;
-extern DCMTK_DCMIOD_EXPORT   const OFConditionConst     IOD_EC_MissingAttribute;
-extern DCMTK_DCMIOD_EXPORT   const OFConditionConst     IOD_EC_MissingSequenceData;
-extern DCMTK_DCMIOD_EXPORT   const OFConditionConst     IOD_EC_InvalidDimensions;
-extern DCMTK_DCMIOD_EXPORT   const OFConditionConst     IOD_EC_CannotInsertFrame;
-extern DCMTK_DCMIOD_EXPORT   const OFConditionConst     IOD_EC_InvalidPixelData;
-extern DCMTK_DCMIOD_EXPORT   const OFConditionConst     IOD_EC_InvalidObject;
-extern DCMTK_DCMIOD_EXPORT   const OFConditionConst     IOD_EC_CannotDecompress;
-extern DCMTK_DCMIOD_EXPORT   const OFConditionConst     IOD_EC_NoSuchRule;
-extern DCMTK_DCMIOD_EXPORT   const OFConditionConst     IOD_EC_InvalidLaterality;
-extern DCMTK_DCMIOD_EXPORT   const OFConditionConst     IOD_EC_InvalidElementValue;
-extern DCMTK_DCMIOD_EXPORT   const OFConditionConst     IOD_EC_InvalidReference;
-extern DCMTK_DCMIOD_EXPORT   const OFConditionConst     IOD_EC_ReferencesOmitted;
-
+extern DCMTK_DCMIOD_EXPORT const OFConditionConst IOD_EC_WrongSOPClass;
+extern DCMTK_DCMIOD_EXPORT const OFConditionConst IOD_EC_MissingAttribute;
+extern DCMTK_DCMIOD_EXPORT const OFConditionConst IOD_EC_MissingSequenceData;
+extern DCMTK_DCMIOD_EXPORT const OFConditionConst IOD_EC_InvalidDimensions;
+extern DCMTK_DCMIOD_EXPORT const OFConditionConst IOD_EC_CannotInsertFrame;
+extern DCMTK_DCMIOD_EXPORT const OFConditionConst IOD_EC_InvalidPixelData;
+extern DCMTK_DCMIOD_EXPORT const OFConditionConst IOD_EC_InvalidObject;
+extern DCMTK_DCMIOD_EXPORT const OFConditionConst IOD_EC_CannotDecompress;
+extern DCMTK_DCMIOD_EXPORT const OFConditionConst IOD_EC_NoSuchRule;
+extern DCMTK_DCMIOD_EXPORT const OFConditionConst IOD_EC_InvalidLaterality;
+extern DCMTK_DCMIOD_EXPORT const OFConditionConst IOD_EC_InvalidElementValue;
+extern DCMTK_DCMIOD_EXPORT const OFConditionConst IOD_EC_InvalidReference;
+extern DCMTK_DCMIOD_EXPORT const OFConditionConst IOD_EC_ReferencesOmitted;
 
 /** Class that wraps some constant definitions in the context of IODs
  */
@@ -67,77 +64,76 @@ class DCMTK_DCMIOD_EXPORT DcmIODTypes
 {
 
 public:
-
-  /** Struct representing a single frame
-   */
-  struct Frame
-  {
-    /// Array for the pixel data bytes
-    Uint8* pixData;
-    /// Number of pixel data bytes (i.e.\ Bits Allocated)
-    size_t length;
-    /// Destructor, frees memory
-    ~Frame() {delete[] pixData;pixData = NULL;}
-  };
-
-  /** IOD Information Entities (incomplete list, extended as needed)
-   */
-  enum IOD_IE
-  {
-    /// Undefined Information Entity (i.e.\ no value set)
-    IE_UNDEFINED,
-    /// Patient Entity
-    IE_PATIENT,
-    /// Study Entity
-    IE_STUDY,
-    /// Series Entity
-    IE_SERIES,
-    /// Frame of Reference Entity
-    IE_FOR,
-    /// Equipment Entity
-    IE_EQUIPMENT,
-    /// Image Entity
-    IE_IMAGE,
-    //// Meta Entity: Instance covering image, waveform, etc.
-    IE_INSTANCE
-  };
-
-  /** Enumerated values for attribute "Laterality"
-   */
-  enum IOD_LATERALITY
-  {
-    /// Undefined (e.g.\ value not set)
-    LATERALITY_UNDEFINED,
-    /// Left body part
-    LATERALITY_L,
-    /// Right body part
-    LATERALITY_R
-  };
-
-  /** Enhanced US Image Module: Image Type (first value)
-   */
-  enum IOD_ENHUSIMAGETYPE
-  {
-    /// Unknown
-    IMAGETYPE_UNKNOWN,
-    /// ORIGINAL
-    IMAGETYPE_ORIGINAL,
-    /// DERIVED
-    IMAGETYPE_DERIVED
-  };
-
+    /** Struct representing a single frame
+     */
+    struct Frame
+    {
+        /// Array for the pixel data bytes
+        Uint8* pixData;
+        /// Number of pixel data bytes (i.e.\ Bits Allocated)
+        size_t length;
+        /// Destructor, frees memory
+        ~Frame()
+        {
+            delete[] pixData;
+            pixData = NULL;
+        }
+    };
+
+    /** IOD Information Entities (incomplete list, extended as needed)
+     */
+    enum IOD_IE
+    {
+        /// Undefined Information Entity (i.e.\ no value set)
+        IE_UNDEFINED,
+        /// Patient Entity
+        IE_PATIENT,
+        /// Study Entity
+        IE_STUDY,
+        /// Series Entity
+        IE_SERIES,
+        /// Frame of Reference Entity
+        IE_FOR,
+        /// Equipment Entity
+        IE_EQUIPMENT,
+        /// Image Entity
+        IE_IMAGE,
+        //// Meta Entity: Instance covering image, waveform, etc.
+        IE_INSTANCE
+    };
+
+    /** Enumerated values for attribute "Laterality"
+     */
+    enum IOD_LATERALITY
+    {
+        /// Undefined (e.g.\ value not set)
+        LATERALITY_UNDEFINED,
+        /// Left body part
+        LATERALITY_L,
+        /// Right body part
+        LATERALITY_R
+    };
+
+    /** Enhanced US Image Module: Image Type (first value)
+     */
+    enum IOD_ENHUSIMAGETYPE
+    {
+        /// Unknown
+        IMAGETYPE_UNKNOWN,
+        /// ORIGINAL
+        IMAGETYPE_ORIGINAL,
+        /// DERIVED
+        IMAGETYPE_DERIVED
+    };
 
 private:
+    /** Private undefined default constructor
+     */
+    DcmIODTypes() {};
 
-  /** Private undefined default constructor
-   */
-  DcmIODTypes() {};
-
-  /** Private undefined destructor
-   */
-  ~DcmIODTypes() {};
-
+    /** Private undefined destructor
+     */
+    ~DcmIODTypes() {};
 };
 
-
 #endif // IODTYPES_H
index ae0098c22e30400a02e53d258948c0ec7ed8d9ac..057082fa252eb26dd0d3dd39e5ceb0a8dc2493fc 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define IODUTIL_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/oftraits.h" // for OFremove_pointer
-#include "dcmtk/ofstd/ofstring.h"
-#include "dcmtk/dcmdata/dcelem.h"
-#include "dcmtk/dcmdata/dcsequen.h"
 #include "dcmtk/dcmdata/dcdatset.h"
 #include "dcmtk/dcmdata/dcdatutl.h"
-#include "dcmtk/ofstd/ofdate.h"
-#include "dcmtk/ofstd/oftime.h"
+#include "dcmtk/dcmdata/dcelem.h"
+#include "dcmtk/dcmdata/dcsequen.h"
 #include "dcmtk/dcmiod/ioddef.h"
 #include "dcmtk/dcmiod/iodrules.h"
 #include "dcmtk/dcmiod/iodtypes.h"
+#include "dcmtk/ofstd/ofdate.h"
+#include "dcmtk/ofstd/ofstring.h"
+#include "dcmtk/ofstd/oftime.h"
+#include "dcmtk/ofstd/oftraits.h" // for OFremove_pointer
 
 /** Class with helper functions used within the dcmiod module (and beyond)
  */
@@ -41,909 +41,975 @@ class DCMTK_DCMIOD_EXPORT DcmIODUtil
 {
 
 public:
-
-  /** Get element from dataset and check it for correct value multiplicity
-   *  and type.
-   *  @param  dataset DICOM dataset from which the element should be retrieved.
-   *          (Would be 'const' if the methods from 'dcmdata' would also
-   *          (be 'const'.)
-   *  @param  delem  DICOM element used to store the value (always creates
-   *          a copy of the dataset element's value)
-   *  @param  vm Value multiplicity (according to the data dictionary) to be
-   *          checked for. (See DcmElement::checkVM() for a list of valid
-   *          values.) Interpreted as cardinality (number of items) for
-   *          sequence attributes.
-   *  @param  type Value type (valid value: "1", "1C", "2", something else
-   *          which is not checked)
-   *  @param  moduleName Optional module name to be printed (NULL: no module
-   *          printed at all)
-   *  @return EC_Normal if element could be retrieved and value is correct,
-   *          an error code otherwise
-   */
-  static OFCondition getAndCheckElementFromDataset(DcmItem &dataset,
-                                                   DcmElement &delem,
-                                                   const OFString &vm,
-                                                   const OFString &type,
-                                                   const char *moduleName = NULL);
-
-  /** Get element from dataset and check it for correct value multiplicity and
-   *  type.
-   *  @param  dataset DICOM dataset from which the element should be retrieved.
-   *          (Would be 'const' if the methods from 'dcmdata' would also
-   *          be 'const')
-   *  @param  tagKey Tag key of the element to get
-   *  @param  delem DICOM element that is set to a copy of the dataset's
-   *          orinal element
-   *  @param  vm Value multiplicity (according to the data dictionary) to be
-   *          checked for. (See DcmElement::checkVM() for a list of valid
-   *          values.) Interpreted as cardinality (number of items) for
-   *          sequence attributes.
-   *  @param  type Value type (valid value: "1", "1C", "2", something else
-   *          which is not checked)
-   *  @param  moduleName Optional module name to be printed (NULL: no module
-   *          printed at all)
-   *  @return EC_Normal if element could be retrieved and value is correct, an
-   *          error code otherwise
-   */
-  static OFCondition getAndCheckElementFromDataset(DcmItem &dataset,
-                                                   const DcmTagKey& tagKey,
-                                                   DcmElement*& delem,
-                                                   const OFString &vm,
-                                                   const OFString &type,
-                                                   const char *moduleName = NULL);
-
-  /** Get element from dataset and check it for correct value multiplicity
-   *  and type.
-   *  @param  dataset DICOM dataset from which the element should be retrieved.
-   *          (Would be 'const' if the methods from 'dcmdata' would also
-   *          be 'const'.)
-   *  @param  delem DICOM element used to store the value (always creates
-   *          a copy of the value from the original element)
-   *  @param  rule  Rule describing parameters to be checked on element
-   *  @return EC_Normal if element could be retrieved and value is correct, an
-   *          error code otherwise
-   */
-  static OFCondition getAndCheckElementFromDataset(DcmItem &dataset,
-                                                   DcmElement &delem,
-                                                   const IODRule* rule);
-
-  /** Get element from dataset and check it for correct value multiplicity
-   *  and type.
-   *  @param  dataset DICOM dataset from which the element should be retrieved.
-   *          (Would be 'const' if the methods from 'dcmdata' would also
-   *          be 'const')
-   *  @param  delem DICOM element that is set to a copy of the dataset's
-   *          orinal element
-   *  @param  rule  Rule describing parameters to be checked on element.
-   *  @return EC_Normal if element could be retrieved and value is correct, an
-   *          error code otherwise
-   */
-  static OFCondition getAndCheckElementFromDataset(DcmItem &dataset,
-                                                   DcmElement*& delem,
-                                                   const IODRule* rule);
-
-  /** Get current date in DICOM 'DA' format (YYYYMMDD)
-   *  @param  dateString String used to store the current date.
-   *          (empty string if current date could not be retrieved)
-   *  @return Resulting character string
-   */
-  static const OFString& currentDate(OFString &dateString);
-
-  /** Get current time in DICOM 'TM' format (HHMMSS)
-   *  The optional UTC notation (e.g.\ +0100) is currently not supported.
-   *  @param  timeString String used to store the current time
-   *                     (empty string if current time could not be retrieved)
-   *  @return Resulting character string, empty if time could not be retrieved
-   */
-  static const OFString& currentTime(OFString &timeString);
-
-  /** Copy given element to the dataset
-   *  The element is only added if 'result' is EC_Normal. A copy of the given
-   *  element is created, i.e.\ the caller is responsible for deleting the
-   *  original element handed to this function (if desired).
-   *  @param  result Reference to status variable (checked before adding and
-   *          updated afterwards!)
-   *  @param  dataset Reference to DICOM dataset to which the element should
-   *          be added
-   *  @param  delem Reference to DICOM element which should be added; a
-   *          copy is created so caller is responsible for deleting delem (if
-   *          desired).
-   *  @param  vm Value multiplicity (according to the data dictionary) to be
-   *          checked for. (See DcmElement::checkVM() for a list of valid
-   *          values.). Interpreted as cardinality (number of items) for
-   *          sequence attributes.
-   *  @param  type  Value type (valid value: "1", "2" or something else which
-   *          is not checked)
-   *  @param  moduleName Optional module name to be printed (NULL: no module
-   *          printed at all)
-   *  @return Current value of 'result', EC_Normal if successful,
-   *          an error code otherwise
-   */
-  static OFCondition copyElementToDataset(OFCondition &result,
-                                          DcmItem &dataset,
-                                          const DcmElement &delem,
-                                          const OFString &vm,
-                                          const OFString &type,
-                                          const char *moduleName = NULL);
-
-  /** Copy given element to the dataset. The element is only added if 'result'
-   *  is EC_Normal.
-   *  @param  result reference to status variable (checked before adding and
-   *          updated afterwards!)
-   *  @param  dataset reference to DICOM dataset to which the element
-   *          should be added
-   *  @param  delem reference to DICOM element which should be added; the value
-   *          is copied from the original dataset's element
-   *  @param  rule  Rule describing parameters to be checked on element.
-   *  @return Current value of 'result', EC_Normal if successful, an error code
-   *          otherwise
-   */
-  static OFCondition copyElementToDataset(OFCondition &result,
-                                          DcmItem &dataset,
-                                          const DcmElement &delem,
-                                          const IODRule* rule);
-
-  /** Add given element to the dataset
-   *  The element is only added if 'result' is EC_Normal and the 'delem'
-   *  pointer is not NULL.
-   *  @param  result Reference to status variable (checked before adding and
-   *          updated afterwards!)
-   *  @param  dataset Reference to DICOM dataset to which the element should
-   *          be added
-   *  @param  delem Pointer to DICOM element which should be added. The element
-   *          is always consumed by this function, i.e.\ insertion was successful
-   *          and therefore ownership is transferred to the dataset, or the
-   *          element is deleted from memory if it could not be inserted.
-   *  @param  rule  Rule describing parameters to be checked on element.
-   *  @return Current value of 'result', EC_Normal if successful, an error code otherwise
-   */
-  static OFCondition addElementToDataset(OFCondition &result,
-                                         DcmItem &dataset,
-                                         DcmElement *delem,
-                                         const IODRule* rule);
-
-  /** Check element value for correct value multiplicity and type.
-   *  @param  delem Pointer to DICOM element to be checked (might be NULL)
-   *  @param  tagKey DICOM tag of the DICOM element the parameter 'delem' points to
-   *  @param  vm Value multiplicity (according to the data dictionary) to be checked for.
-   *          (See DcmElement::checkVM() for a list of valid values.)
-   *          Interpreted as cardinality (number of items) for sequence attributes.
-   *  @param  type Value type (valid value: "1", "1C", "2", something else)
-   *  @param  searchCond Optional flag indicating the status of a previous 'search' function call
-   *  @param  moduleName Optional module name to be printed (default: "IOD" if NULL)
-   *  @param  logLevel The log level to log errors to
-   *  @return EC_Normal if element value is correct, error otherwise
-   */
-  static OFCondition checkElementValue(const DcmElement *delem,
-                                       const DcmTagKey &tagKey,
-                                       const OFString &vm,
-                                       const OFString &type,
-                                       const OFCondition &searchCond = EC_Normal,
-                                       const char *moduleName = NULL,
-                                       const dcmtk::log4cplus::LogLevel logLevel = dcmtk::log4cplus::WARN_LOG_LEVEL);
-
-  /** Check element value for correct value multiplicity and type.
-   *  @param  delem DICOM element to be checked
-   *  @param  vm Value multiplicity (according to the data dictionary) to be checked for.
-   *          (See DcmElement::checkVM() for a list of valid values.)
-   *          Interpreted as cardinality (number of items) for sequence attributes.
-   *  @param  type Value type (valid value: "1", "1C", "2", something else)
-   *  @param  searchCond Optional flag indicating the status of a previous 'search' function call
-   *  @param  moduleName Optional module name to be printed (default: "IOD" if NULL)
-   *  @param  logLevel The log level to log errors to
-   *  @return EC_Normal if element value is correct, error otherwise
-   */
-  static OFCondition checkElementValue(const DcmElement &delem,
-                                       const OFString &vm,
-                                       const OFString &type,
-                                       const OFCondition &searchCond = EC_Normal,
-                                       const char *moduleName = NULL,
-                                       const dcmtk::log4cplus::LogLevel logLevel = dcmtk::log4cplus::WARN_LOG_LEVEL);
-
-  /** Get string value from element
-   *  @param  delem DICOM element from which the string value should be retrieved
-   *  @param  stringValue Reference to variable in which the result should be stored.
-   *          (This parameter is automatically cleared if an error occurs.)
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  static OFCondition getStringValueFromElement(const DcmElement &delem,
-                                               OFString &stringValue,
-                                               const signed long pos);
-
-  /** Get string value from item
-   *  @param  key The tag key of the attribute whose value should be retrieved
-   *  @param  item The item to search the attribute in
-   *  @param  result Reference to variable in which the result should be stored.
-   *          (This parameter is automatically cleared if an error occurs.)
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  static OFCondition getStringValueFromItem(const DcmTagKey& key,
-                                            DcmItem& item,
-                                            OFString& result,
-                                            const signed long& pos);
-
-  /** Get Float64 value from item
-   *  @param  key The tag key of the attribute whose value should be retrieved
-   *  @param  item The item to search the attribute in
-   *  @param  result Reference to variable in which the result should be stored.
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  static OFCondition getFloat64ValueFromItem(const DcmTagKey& key,
-                                             DcmItem& item,
-                                             Float64& result,
-                                             const unsigned long& pos);
-
-  /** Get Float64 values from item
-   *  @param  key The tag key of the attribute whose value should be retrieved
-   *  @param  item The item to search the attribute in
-   *  @param  result Reference to variable in which the result should be stored.
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  static OFCondition getFloat64ValuesFromItem(const DcmTagKey& key,
-                                              DcmItem& item,
-                                              OFVector<Float64>& result);
-
-  /** Get Float64 value from element
-   *  @param  delem The element whose value should be retrieved
-   *  @param  result Reference to variable in which the result should be stored.
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  static OFCondition getFloat64ValueFromElement(const DcmElement &delem,
-                                                Float64& result,
-                                                const unsigned long pos);
-
-  /** Get Float64 values from element
-   *  @param  delem The element to get the value from
-   *  @param  result Reference to variable in which the result should be stored.
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  static OFCondition getFloat64ValuesFromElement(const DcmElement &delem,
-                                                 OFVector<Float64>& result);
-
-  /** Set a DcmElement's content from Uint16 vector
-   *  @param  delem DICOM element to be filled
-   *  @param  values Vector use as a source for the values
-   *  @param  vm Value multiplicity (according to the data dictionary) to be
-   *           checked for. (See DcmElement::checkVM() for a list of
-   *           valid values.)
-   *  @param  check If OFTrue, then it is checked whether number of values
-   *          conforms to the value provided by the vm parameter.
-   *  @return Dtatus, EC_Normal if successful, an error code otherwise
-   */
-  static OFCondition setUint16ValuesOnElement(DcmElement &delem,
-                                              const OFVector<Uint16>& values,
-                                              const OFString& vm,
-                                              const OFBool check);
-
-  /** Get Uint16 values from DcmElement
-   *  @param  delem  DICOM element to read from
-   *  @param  values Vector used as destination for the values
-   *  @return Status EC_Normal if successful, an error code otherwise
-   */
-  static OFCondition getUint16ValuesFromElement(DcmElement &delem,
-                                                OFVector<Uint16>& values);
-
-  /** Returns single item from given sequence. Returns error number of items
-   *  is 0 or more than 1.
-   *  @param  seq Sequence to read from.
-   *  @param  item The resulting item, NULL in case of error
-   *  @param  checkKey If given it is checked whether the given seq parameter
-   *          matches the tag key provided in the checkKey parameter. If
-   *          not, an error is returned.
-   *  @return Status EC_Normal if successful, an error code otherwise
-   */
-  static OFCondition getAndCheckSingleItem(DcmSequenceOfItems& seq,
-                                           DcmItem*& item,
-                                           const DcmTagKey& checkKey = DCM_UndefinedTagKey);
-
-  /** Copies Uint8 values from given element to destination container
-   *  (must support push_back() method).
-   *  @param elem the element to read from. If NULL, an error is returned.
-   *  @param destination the container to store the Uint8 values to
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  template <class Container>
-  static OFCondition copyFromUint8Array(DcmElement* elem,
-                                        Container& destination)
-  {
-    if (elem == NULL)
-    return EC_IllegalParameter;
-
-    size_t numValues = elem->getNumberOfValues();
-    OFCondition result;
-    for (size_t count = 0; (count < numValues) && result.good(); count ++)
-    {
-      Uint8 value;
-      result = elem->getUint8(value, OFstatic_cast(unsigned long, count));
-      if ( result.good() )
-      {
-        destination.push_back(value);
-      }
-    }
-    if ( result.bad() )
+    /** Get element from dataset and check it for correct value multiplicity
+     *  and type.
+     *  @param  dataset DICOM dataset from which the element should be retrieved.
+     *          (Would be 'const' if the methods from 'dcmdata' would also
+     *          (be 'const'.)
+     *  @param  delem  DICOM element used to store the value (always creates
+     *          a copy of the dataset element's value)
+     *  @param  vm Value multiplicity (according to the data dictionary) to be
+     *          checked for. (See DcmElement::checkVM() for a list of valid
+     *          values.) Interpreted as cardinality (number of items) for
+     *          sequence attributes.
+     *  @param  type Value type (valid value: "1", "1C", "2", something else
+     *          which is not checked)
+     *  @param  moduleName Optional module name to be printed (NULL: no module
+     *          printed at all)
+     *  @return EC_Normal if element could be retrieved and value is correct,
+     *          an error code otherwise
+     */
+    static OFCondition getAndCheckElementFromDataset(
+        DcmItem& dataset, DcmElement& delem, const OFString& vm, const OFString& type, const char* moduleName = NULL);
+
+    /** Get element from dataset and check it for correct value multiplicity and
+     *  type.
+     *  @param  dataset DICOM dataset from which the element should be retrieved.
+     *          (Would be 'const' if the methods from 'dcmdata' would also
+     *          be 'const')
+     *  @param  tagKey Tag key of the element to get
+     *  @param  delem DICOM element that is set to a copy of the dataset's
+     *          orinal element
+     *  @param  vm Value multiplicity (according to the data dictionary) to be
+     *          checked for. (See DcmElement::checkVM() for a list of valid
+     *          values.) Interpreted as cardinality (number of items) for
+     *          sequence attributes.
+     *  @param  type Value type (valid value: "1", "1C", "2", something else
+     *          which is not checked)
+     *  @param  moduleName Optional module name to be printed (NULL: no module
+     *          printed at all)
+     *  @return EC_Normal if element could be retrieved and value is correct, an
+     *          error code otherwise
+     */
+    static OFCondition getAndCheckElementFromDataset(DcmItem& dataset,
+                                                     const DcmTagKey& tagKey,
+                                                     DcmElement*& delem,
+                                                     const OFString& vm,
+                                                     const OFString& type,
+                                                     const char* moduleName = NULL);
+
+    /** Get element from dataset and check it for correct value multiplicity
+     *  and type.
+     *  @param  dataset DICOM dataset from which the element should be retrieved.
+     *          (Would be 'const' if the methods from 'dcmdata' would also
+     *          be 'const'.)
+     *  @param  delem DICOM element used to store the value (always creates
+     *          a copy of the value from the original element)
+     *  @param  rule  Rule describing parameters to be checked on element
+     *  @return EC_Normal if element could be retrieved and value is correct, an
+     *          error code otherwise
+     */
+    static OFCondition getAndCheckElementFromDataset(DcmItem& dataset, DcmElement& delem, const IODRule* rule);
+
+    /** Get element from dataset and check it for correct value multiplicity
+     *  and type.
+     *  @param  dataset DICOM dataset from which the element should be retrieved.
+     *          (Would be 'const' if the methods from 'dcmdata' would also
+     *          be 'const')
+     *  @param  delem DICOM element that is set to a copy of the dataset's
+     *          orinal element
+     *  @param  rule  Rule describing parameters to be checked on element.
+     *  @return EC_Normal if element could be retrieved and value is correct, an
+     *          error code otherwise
+     */
+    static OFCondition getAndCheckElementFromDataset(DcmItem& dataset, DcmElement*& delem, const IODRule* rule);
+
+    /** Get current date in DICOM 'DA' format (YYYYMMDD)
+     *  @param  dateString String used to store the current date.
+     *          (empty string if current date could not be retrieved)
+     *  @return Resulting character string
+     */
+    static const OFString& currentDate(OFString& dateString);
+
+    /** Get current time in DICOM 'TM' format (HHMMSS)
+     *  The optional UTC notation (e.g.\ +0100) is currently not supported.
+     *  @param  timeString String used to store the current time
+     *                     (empty string if current time could not be retrieved)
+     *  @return Resulting character string, empty if time could not be retrieved
+     */
+    static const OFString& currentTime(OFString& timeString);
+
+    /** Copy given element to the dataset
+     *  The element is only added if 'result' is EC_Normal. A copy of the given
+     *  element is created, i.e.\ the caller is responsible for deleting the
+     *  original element handed to this function (if desired).
+     *  @param  result Reference to status variable (checked before adding and
+     *          updated afterwards!)
+     *  @param  dataset Reference to DICOM dataset to which the element should
+     *          be added
+     *  @param  delem Reference to DICOM element which should be added; a
+     *          copy is created so caller is responsible for deleting delem (if
+     *          desired).
+     *  @param  vm Value multiplicity (according to the data dictionary) to be
+     *          checked for. (See DcmElement::checkVM() for a list of valid
+     *          values.). Interpreted as cardinality (number of items) for
+     *          sequence attributes.
+     *  @param  type  Value type (valid value: "1", "2" or something else which
+     *          is not checked)
+     *  @param  moduleName Optional module name to be printed (NULL: no module
+     *          printed at all)
+     *  @return Current value of 'result', EC_Normal if successful,
+     *          an error code otherwise
+     */
+    static OFCondition copyElementToDataset(OFCondition& result,
+                                            DcmItem& dataset,
+                                            const DcmElement& delem,
+                                            const OFString& vm,
+                                            const OFString& type,
+                                            const char* moduleName = NULL);
+
+    /** Copy given element to the dataset. The element is only added if 'result'
+     *  is EC_Normal.
+     *  @param  result reference to status variable (checked before adding and
+     *          updated afterwards!)
+     *  @param  dataset reference to DICOM dataset to which the element
+     *          should be added
+     *  @param  delem reference to DICOM element which should be added; the value
+     *          is copied from the original dataset's element
+     *  @param  rule  Rule describing parameters to be checked on element.
+     *  @return Current value of 'result', EC_Normal if successful, an error code
+     *          otherwise
+     */
+    static OFCondition
+    copyElementToDataset(OFCondition& result, DcmItem& dataset, const DcmElement& delem, const IODRule* rule);
+
+    /** Add given element to the dataset
+     *  The element is only added if 'result' is EC_Normal and the 'delem'
+     *  pointer is not NULL.
+     *  @param  result Reference to status variable (checked before adding and
+     *          updated afterwards!)
+     *  @param  dataset Reference to DICOM dataset to which the element should
+     *          be added
+     *  @param  delem Pointer to DICOM element which should be added. The element
+     *          is always consumed by this function, i.e.\ insertion was successful
+     *          and therefore ownership is transferred to the dataset, or the
+     *          element is deleted from memory if it could not be inserted.
+     *  @param  rule  Rule describing parameters to be checked on element.
+     *  @return Current value of 'result', EC_Normal if successful, an error code otherwise
+     */
+    static OFCondition
+    addElementToDataset(OFCondition& result, DcmItem& dataset, DcmElement* delem, const IODRule* rule);
+
+    /** Check element value for correct value multiplicity and type.
+     *  @param  delem Pointer to DICOM element to be checked (might be NULL)
+     *  @param  tagKey DICOM tag of the DICOM element the parameter 'delem' points to
+     *  @param  vm Value multiplicity (according to the data dictionary) to be checked for.
+     *          (See DcmElement::checkVM() for a list of valid values.)
+     *          Interpreted as cardinality (number of items) for sequence attributes.
+     *  @param  type Value type (valid value: "1", "1C", "2", something else)
+     *  @param  searchCond Optional flag indicating the status of a previous 'search' function call
+     *  @param  moduleName Optional module name to be printed (default: "IOD" if NULL)
+     *  @param  logLevel The log level to log errors to
+     *  @return EC_Normal if element value is correct, error otherwise
+     */
+    static OFCondition checkElementValue(const DcmElement* delem,
+                                         const DcmTagKey& tagKey,
+                                         const OFString& vm,
+                                         const OFString& type,
+                                         const OFCondition& searchCond             = EC_Normal,
+                                         const char* moduleName                    = NULL,
+                                         const dcmtk::log4cplus::LogLevel logLevel = dcmtk::log4cplus::WARN_LOG_LEVEL);
+
+    /** Check element value for correct value multiplicity and type.
+     *  @param  delem DICOM element to be checked
+     *  @param  vm Value multiplicity (according to the data dictionary) to be checked for.
+     *          (See DcmElement::checkVM() for a list of valid values.)
+     *          Interpreted as cardinality (number of items) for sequence attributes.
+     *  @param  type Value type (valid value: "1", "1C", "2", something else)
+     *  @param  searchCond Optional flag indicating the status of a previous 'search' function call
+     *  @param  moduleName Optional module name to be printed (default: "IOD" if NULL)
+     *  @param  logLevel The log level to log errors to
+     *  @return EC_Normal if element value is correct, error otherwise
+     */
+    static OFCondition checkElementValue(const DcmElement& delem,
+                                         const OFString& vm,
+                                         const OFString& type,
+                                         const OFCondition& searchCond             = EC_Normal,
+                                         const char* moduleName                    = NULL,
+                                         const dcmtk::log4cplus::LogLevel logLevel = dcmtk::log4cplus::WARN_LOG_LEVEL);
+
+    /** Get string value from element
+     *  @param  delem DICOM element from which the string value should be retrieved
+     *  @param  stringValue Reference to variable in which the result should be stored.
+     *          (This parameter is automatically cleared if an error occurs.)
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    static OFCondition getStringValueFromElement(const DcmElement& delem, OFString& stringValue, const signed long pos);
+
+    /** Get string value from item
+     *  @param  key The tag key of the attribute whose value should be retrieved
+     *  @param  item The item to search the attribute in
+     *  @param  result Reference to variable in which the result should be stored.
+     *          (This parameter is automatically cleared if an error occurs.)
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    static OFCondition
+    getStringValueFromItem(const DcmTagKey& key, DcmItem& item, OFString& result, const signed long& pos);
+
+    /** Get Float64 value from item
+     *  @param  key The tag key of the attribute whose value should be retrieved
+     *  @param  item The item to search the attribute in
+     *  @param  result Reference to variable in which the result should be stored.
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    static OFCondition
+    getFloat64ValueFromItem(const DcmTagKey& key, DcmItem& item, Float64& result, const unsigned long& pos);
+
+    /** Get Float64 values from item
+     *  @param  key The tag key of the attribute whose value should be retrieved
+     *  @param  item The item to search the attribute in
+     *  @param  result Reference to variable in which the result should be stored.
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    static OFCondition getFloat64ValuesFromItem(const DcmTagKey& key, DcmItem& item, OFVector<Float64>& result);
+
+    /** Get Float64 value from element
+     *  @param  delem The element whose value should be retrieved
+     *  @param  result Reference to variable in which the result should be stored.
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    static OFCondition getFloat64ValueFromElement(const DcmElement& delem, Float64& result, const unsigned long pos);
+
+    /** Get Float64 values from element
+     *  @param  delem The element to get the value from
+     *  @param  result Reference to variable in which the result should be stored.
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    static OFCondition getFloat64ValuesFromElement(const DcmElement& delem, OFVector<Float64>& result);
+
+    /** Set a DcmElement's content from Float64 vector
+     *  @param  delem DICOM element to be filled
+     *  @param  values Vector use as a source for the values
+     *  @param  vm Value multiplicity (according to the data dictionary) to be
+     *           checked for. (See DcmElement::checkVM() for a list of
+     *           valid values.)
+     *  @param  check If OFTrue, then it is checked whether number of values
+     *          conforms to the value provided by the vm parameter.
+     *  @return Dtatus, EC_Normal if successful, an error code otherwise
+     */
+    static OFCondition setFloat64ValuesOnElement(DcmElement& delem,
+                                                 const OFVector<Float64>& values,
+                                                 const OFString& vm,
+                                                 const OFBool check);
+
+    /** Get Float32 value from element
+     *  @param  delem The element whose value should be retrieved
+     *  @param  result Reference to variable in which the result should be stored.
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    static OFCondition getFloat32ValueFromElement(const DcmElement& delem, Float32& result, const unsigned long pos);
+
+    /** Set a DcmElement's content from Float32 vector
+     *  @param  delem DICOM element to be filled
+     *  @param  values Vector use as a source for the values
+     *  @param  vm Value multiplicity (according to the data dictionary) to be
+     *           checked for. (See DcmElement::checkVM() for a list of
+     *           valid values.)
+     *  @param  check If OFTrue, then it is checked whether number of values
+     *          conforms to the value provided by the vm parameter.
+     *  @return Dtatus, EC_Normal if successful, an error code otherwise
+     */
+    static OFCondition setFloat32ValuesOnElement(DcmElement& delem,
+                                                 const OFVector<Float32>& values,
+                                                 const OFString& vm,
+                                                 const OFBool check);
+
+    /** Set a DcmElement's content from Uint16 vector
+     *  @param  delem DICOM element to be filled
+     *  @param  values Vector use as a source for the values
+     *  @param  vm Value multiplicity (according to the data dictionary) to be
+     *           checked for. (See DcmElement::checkVM() for a list of
+     *           valid values.)
+     *  @param  check If OFTrue, then it is checked whether number of values
+     *          conforms to the value provided by the vm parameter.
+     *  @return Dtatus, EC_Normal if successful, an error code otherwise
+     */
+    static OFCondition
+    setUint16ValuesOnElement(DcmElement& delem, const OFVector<Uint16>& values, const OFString& vm, const OFBool check);
+
+    /** Get Uint16 values from DcmElement
+     *  @param  delem  DICOM element to read from
+     *  @param  values Vector used as destination for the values
+     *  @return Status EC_Normal if successful, an error code otherwise
+     */
+    static OFCondition getUint16ValuesFromElement(DcmElement& delem, OFVector<Uint16>& values);
+
+    /** Returns single item from given sequence. Returns error number of items
+     *  is 0 or more than 1.
+     *  @param  seq Sequence to read from.
+     *  @param  item The resulting item, NULL in case of error
+     *  @param  checkKey If given it is checked whether the given seq parameter
+     *          matches the tag key provided in the checkKey parameter. If
+     *          not, an error is returned.
+     *  @return Status EC_Normal if successful, an error code otherwise
+     */
+    static OFCondition
+    getAndCheckSingleItem(DcmSequenceOfItems& seq, DcmItem*& item, const DcmTagKey& checkKey = DCM_UndefinedTagKey);
+
+    /** Copies Uint8 values from given element to destination container
+     *  (must support push_back() method).
+     *  @param elem the element to read from. If NULL, an error is returned.
+     *  @param destination the container to store the Uint8 values to
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    template <class Container>
+    static OFCondition copyFromUint8Array(DcmElement* elem, Container& destination)
     {
-      destination.clear();
-    }
-    return result;
-  }
-
-  /** Check whether SOP class UID matches the expected value
-   *  @param  item Item to read from. NULL value causes error return value.
-   *  @param  desiredSOPClass The value that is expected
-   *  @param  valueFound The value actually found (empty if no value could
-   *          be retrieved)
-   *  @return EC_Normal if value could be found and equals expected value,
-   *          EC_TagNotFound if SOP Class UID is not found in dataset,
-   *          EC_InvalidValue if SOP class differs from expected value.
-   */
-  static OFCondition checkSOPClass(DcmItem* item,
-                                   const OFString& desiredSOPClass,
-                                   OFString& valueFound);
-
-  /** Check whether given tag is a sequence tag
-   *  @param  key the tag key to be checked
-   *  @param  privateCreator The private creator to check for if tag is private
-   *  @return OFTrue if given tag is a sequence tag, OFFalse otherwise
-   */
-  static OFBool isSequenceTag(const DcmTagKey& key,
-                              const OFString& privateCreator = "");
-
-  /** Reads items from DICOM sequence into container by creating a dedicated
-   *  container item for each DICOM item. The container must support
-   *  push_back(T) function and the container's element type T must support
-   *  the read(DcmItem*) function.
-   *  @param  source The source sequence to read items from
-   *  @param  seqKey The sequence's tag key that is expected
-   *  @param  destination The destination container to read into
-   *  @param  cardinality Expected number of items.
-   *          See DcmElement::checkVM() for a list of valid values.
-   *  @param  type The sequence type as noted in part 3 of the DICOM standard,
-   *          i.e.\ "1,1C,2,2C or 3".
-   *  @param  module Name of the module/macro this sequence is contained in. Used
-   *          for error messages and can also be left empty.
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  template <class Container>
-  static OFCondition readSubSequence(DcmSequenceOfItems* source,
-                                    const DcmTagKey& seqKey,
-                                    Container& destination,
-                                    const OFString& cardinality,
-                                    const OFString& type,
-                                    const OFString& module)
-  {
-    OFCondition result;
-    OFCondition exists = EC_Normal;
-    if (!source)
-      exists = EC_TagNotFound;
-
-    /* Check sequence and report errors as warnings, read anyway */
-    checkElementValue(source, seqKey, cardinality, type, exists, module.c_str());
-    if (source)
-    {
-      DcmItem *item = OFstatic_cast(DcmItem*, source->nextInContainer(NULL));
-      size_t count = 0;
-      while (item != NULL)
-      {
-        if (item != NULL)
+        if (elem == NULL)
+            return EC_IllegalParameter;
+
+        size_t numValues = elem->getNumberOfValues();
+        OFCondition result;
+        for (size_t count = 0; (count < numValues) && result.good(); count++)
         {
-          // define the element type
-          typedef typename OFremove_pointer<typename Container::value_type>::type Element;
-          Element *newElem = new Element();
-          // read into container item (clears old data first)
-          if ( newElem != NULL)
-          {
-            result = (newElem)->read(*item, OFFalse /* no need to delete anything */);
-            if ( result.good() )
+            Uint8 value;
+            result = elem->getUint8(value, OFstatic_cast(unsigned long, count));
+            if (result.good())
             {
-              destination.push_back(newElem);
+                destination.push_back(value);
             }
-            else
+        }
+        if (result.bad())
+        {
+            destination.clear();
+        }
+        return result;
+    }
+
+    /** Check whether SOP class UID matches the expected value
+     *  @param  item Item to read from. NULL value causes error return value.
+     *  @param  desiredSOPClass The value that is expected
+     *  @param  valueFound The value actually found (empty if no value could
+     *          be retrieved)
+     *  @return EC_Normal if value could be found and equals expected value,
+     *          EC_TagNotFound if SOP Class UID is not found in dataset,
+     *          EC_InvalidValue if SOP class differs from expected value.
+     */
+    static OFCondition checkSOPClass(DcmItem* item, const OFString& desiredSOPClass, OFString& valueFound);
+
+    /** Check whether given tag is a sequence tag
+     *  @param  key the tag key to be checked
+     *  @param  privateCreator The private creator to check for if tag is private
+     *  @return OFTrue if given tag is a sequence tag, OFFalse otherwise
+     */
+    static OFBool isSequenceTag(const DcmTagKey& key, const OFString& privateCreator = "");
+
+    /** Reads items from DICOM sequence into container by creating a dedicated
+     *  container item for each DICOM item. The container must support
+     *  push_back(T) function and the container's element type T must support
+     *  the read(DcmItem*) function.
+     *  @param  source The source sequence to read items from
+     *  @param  seqKey The sequence's tag key that is expected
+     *  @param  destination The destination container to read into
+     *  @param  cardinality Expected number of items.
+     *          See DcmElement::checkVM() for a list of valid values.
+     *  @param  type The sequence type as noted in part 3 of the DICOM standard,
+     *          i.e.\ "1,1C,2,2C or 3".
+     *  @param  module Name of the module/macro this sequence is contained in. Used
+     *          for error messages and can also be left empty.
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    template <class Container>
+    static OFCondition readSubSequence(DcmSequenceOfItems* source,
+                                       const DcmTagKey& seqKey,
+                                       Container& destination,
+                                       const OFString& cardinality,
+                                       const OFString& type,
+                                       const OFString& module)
+    {
+        OFCondition result;
+        OFCondition exists = EC_Normal;
+        if (!source)
+            exists = EC_TagNotFound;
+
+        /* Check sequence and report errors as warnings, read anyway */
+        checkElementValue(source, seqKey, cardinality, type, exists, module.c_str());
+        if (source)
+        {
+            DcmItem* item = OFstatic_cast(DcmItem*, source->nextInContainer(NULL));
+            size_t count  = 0;
+            while (item != NULL)
             {
-              delete newElem;
-              DCMIOD_WARN("Could not read item #" << count << " from " << DcmTag(source->getTag()).getTagName() << " (skipping item): " << result.text());
+                if (item != NULL)
+                {
+                    // define the element type
+                    typedef typename OFremove_pointer<typename Container::value_type>::type Element;
+                    Element* newElem = new Element();
+                    // read into container item (clears old data first)
+                    if (newElem != NULL)
+                    {
+                        result = (newElem)->read(*item, OFFalse /* no need to delete anything */);
+                        if (result.good())
+                        {
+                            destination.push_back(newElem);
+                        }
+                        else
+                        {
+                            delete newElem;
+                            DCMIOD_WARN("Could not read item #" << count << " from "
+                                                                << DcmTag(source->getTag()).getTagName()
+                                                                << " (skipping item): " << result.text());
+                        }
+                    }
+                    else
+                    {
+                        DCMIOD_ERROR("Could not store data from item #" << count << " from "
+                                                                        << DcmTag(source->getTag()).getTagName()
+                                                                        << " (skipping item): Memory exhausted?");
+                    }
+                }
+                else
+                {
+                    DCMIOD_WARN("Could not get item #" << count << " from " << DcmTag(source->getTag()).getTagName()
+                                                       << " (malformed data or internal error), skipping item");
+                }
+                item = OFstatic_cast(DcmItem*, source->nextInContainer(item));
+                count++;
             }
-          }
-          else
-          {
-            DCMIOD_ERROR("Could not store data from item #" << count << " from " << DcmTag(source->getTag()).getTagName() << " (skipping item): Memory exhausted?");
-          }
         }
         else
         {
-          DCMIOD_WARN("Could not get item #" << count << " from " <<  DcmTag(source->getTag()).getTagName() << " (malformed data or internal error), skipping item");
+            result = EC_IllegalParameter;
         }
-        item = OFstatic_cast(DcmItem*, source->nextInContainer(item));
-        count++;
-      }
+        return result;
     }
-    else
+
+    /** Reads DICOM sequence into container by creating a dedicated container element
+     *  for each DICOM item. The container must support push_back(T) function
+     *  and the container's element type T must support the read(DcmItem*) function.
+     *  @param  source The source DICOM item read the sequence from
+     *  @param  seqKey The tag key of the sequence to be read
+     *  @param  destination The destination container to read into
+     *  @param  cardinality Expected number of items.
+     *          See DcmElement::checkVM() for a list of valid values.
+     *  @param  type The sequence type as noted in part 3 of the DICOM standard,
+     *          i.e.\ "1,1C,2,2C or 3".
+     *  @param  module Name of the module/macro this sequence is contained in. Used
+     *          for error messages and can also be left empty.
+     *  @return status EC_Normal if successful, an error code otherwise
+     */
+    template <class Container>
+    static OFCondition readSubSequence(DcmItem& source,
+                                       const DcmTagKey& seqKey,
+                                       Container& destination,
+                                       const OFString& cardinality,
+                                       const OFString& type,
+                                       const OFString& module)
     {
-      result = EC_IllegalParameter;
+        OFCondition result;
+        DcmSequenceOfItems* seq = NULL;
+
+        /* Get sequence and read it */
+        source.findAndGetSequence(seqKey, seq);
+        result = readSubSequence(seq, seqKey, destination, cardinality, type, module);
+        return result;
     }
-    return result;
-  }
-
-
-  /** Reads DICOM sequence into container by creating a dedicated container element
-   *  for each DICOM item. The container must support push_back(T) function
-   *  and the container's element type T must support the read(DcmItem*) function.
-   *  @param  source The source DICOM item read the sequence from
-   *  @param  seqKey The tag key of the sequence to be read
-   *  @param  destination The destination container to read into
-   *  @param  cardinality Expected number of items.
-   *          See DcmElement::checkVM() for a list of valid values.
-   *  @param  type The sequence type as noted in part 3 of the DICOM standard,
-   *          i.e.\ "1,1C,2,2C or 3".
-   *  @param  module Name of the module/macro this sequence is contained in. Used
-   *          for error messages and can also be left empty.
-   *  @return status EC_Normal if successful, an error code otherwise
-   */
-  template <class Container>
-  static OFCondition readSubSequence(DcmItem& source,
-                                     const DcmTagKey& seqKey,
-                                     Container& destination,
-                                     const OFString& cardinality,
-                                     const OFString& type,
-                                     const OFString& module)
-  {
-    OFCondition result;
-    DcmSequenceOfItems *seq = NULL;
-
-    /* Get sequence and read it */
-    source.findAndGetSequence(seqKey, seq);
-    result = readSubSequence(seq, seqKey, destination, cardinality, type, module );
-    return result;
-  }
-
-
-  /** Reads DICOM sequence into container by creating a dedicated container
-   *  element for each DICOM item. The container must support the
-   *  push_back(T) function and the container's element type T must support
-   *  the read(DcmItem*) function.
-   *  @param  source The source DICOM item read the sequence from
-   *  @param  seqKey The tag key of the sequence to be read
-   *  @param  destination The destination container to read into
-   *  @param  rule The rule for reading this sequence. If NULL, an error is returned.
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  template <class Container>
-  static OFCondition readSubSequence(DcmItem& source,
-                                     const DcmTagKey& seqKey,
-                                     Container& destination,
-                                     IODRule *rule)
-  {
-    if (rule == NULL)
+
+    /** Reads DICOM sequence into container by creating a dedicated container
+     *  element for each DICOM item. The container must support the
+     *  push_back(T) function and the container's element type T must support
+     *  the read(DcmItem*) function.
+     *  @param  source The source DICOM item read the sequence from
+     *  @param  seqKey The tag key of the sequence to be read
+     *  @param  destination The destination container to read into
+     *  @param  rule The rule for reading this sequence. If NULL, an error is returned.
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    template <class Container>
+    static OFCondition readSubSequence(DcmItem& source, const DcmTagKey& seqKey, Container& destination, IODRule* rule)
     {
-      DCMIOD_ERROR("Cannot read sequence " << seqKey << " (no rule supplied)");
-      return IOD_EC_NoSuchRule;
+        if (rule == NULL)
+        {
+            DCMIOD_ERROR("Cannot read sequence " << seqKey << " (no rule supplied)");
+            return IOD_EC_NoSuchRule;
+        }
+        return readSubSequence<Container>(
+            source, seqKey, destination, rule->getVM(), rule->getType(), rule->getModule());
     }
-    return readSubSequence<Container>(source, seqKey, destination, rule->getVM(), rule->getType(), rule->getModule());
-  }
-
-
-  /** Reads single DICOM item from a specific sequence into a destination class.
-   *  The container must support the read(DcmItem) function. If a single item
-   *  (i.e.\ the first item of the specified sequence) cannot be read, an error
-   *  is returned.
-   *  @param  source The source DICOM item read the sequence from
-   *  @param  seqKey The tag key of the sequence to be read
-   *  @param  destination The destination container to read into
-   *          See DcmElement::checkVM() for a list of valid values.
-   *  @param  type The sequence type as noted in part 3 of the DICOM standard,
-   *          i.e.\ "1,1C,2,2C or 3".
-   *  @param  module Name of the module/macro this sequence is contained in.
-   *          Used for error messages and can also be left empty.
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  template <class Container>
-  static OFCondition readSingleItem(DcmItem& source,
-                                    const DcmTagKey& seqKey,
-                                    Container& destination,
-                                    const OFString& type,
-                                    const OFString& module)
-  {
-    OFCondition result;
-    /* Check sequence, reports cardinality and type errors as warnings */
-    checkSubSequence(result, source, seqKey, "1", type, module, dcmtk::log4cplus::WARN_LOG_LEVEL);
-
-    /* Try to read sequence into internal data (ignore errors as much as possible) */
-    DcmItem* item = NULL;
-    result = source.findAndGetSequenceItem(seqKey, item, 0);
-    if (item != NULL)
+
+    /** Reads single DICOM item from a specific sequence into a destination class.
+     *  The container must support the read(DcmItem) function. If a single item
+     *  (i.e.\ the first item of the specified sequence) cannot be read, an error
+     *  is returned.
+     *  @param  source The source DICOM item read the sequence from
+     *  @param  seqKey The tag key of the sequence to be read
+     *  @param  destination The destination container to read into
+     *  @param  type The sequence type as noted in part 3 of the DICOM standard,
+     *          i.e.\ "1,1C,2,2C or 3".
+     *  @param  module Name of the module/macro this sequence is contained in.
+     *          Used for error messages and can also be left empty.
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    template <class Container>
+    static OFCondition readSingleItem(
+        DcmItem& source, const DcmTagKey& seqKey, Container& destination, const OFString& type, const OFString& module)
     {
-      // read into Container (clears old data first)
-      result = destination.read(*item, OFTrue /* clear old data */);
+        OFCondition result;
+        /* Check sequence, reports cardinality and type errors as warnings */
+        checkSubSequence(result, source, seqKey, "1", type, module, dcmtk::log4cplus::WARN_LOG_LEVEL);
+
+        /* Try to read sequence into internal data (ignore errors as much as possible) */
+        DcmItem* item = NULL;
+        result        = source.findAndGetSequenceItem(seqKey, item, 0);
+        if (item != NULL)
+        {
+            // read into Container (clears old data first)
+            result = destination.read(*item, OFTrue /* clear old data */);
+        }
+        return result;
     }
-    return result;
-  }
-
-  /** Reads single DICOM item from a specific sequence into a destination class.
-   *  The container must support the read(DcmItem) function. If a single item
-   *  (i.e.\ the first item of the specified sequence) cannot be read, an error
-   *  is returned.
-   *  @param  source The source DICOM item read the sequence from
-   *  @param  seqKey The tag key of the sequence to be read
-   *  @param  destination The destination container to read into
-   *          See DcmElement::checkVM() for a list of valid values.
-   *  @param  rule The rule (for the sequence) used for reading.
-   *  @return EC_Normal if successful, an error code otherwise.  If the rule
-   *          equlas NULL, then nothing is read at all and an error is returned
-   *          (IOD_EC_NoSuchRule), but no error is reported to the logger.
-   */
-  template <class Container>
-  static OFCondition readSingleItem(DcmItem& source,
-                                    const DcmTagKey& seqKey,
-                                    Container& destination,
-                                    IODRule *rule = NULL)
-  {
-    if (rule == NULL)
+
+    /** Reads single DICOM item from a specific sequence into a destination class.
+     *  The container must support the read(DcmItem) function. If a single item
+     *  (i.e.\ the first item of the specified sequence) cannot be read, an error
+     *  is returned.
+     *  @param  source The source DICOM item read the sequence from
+     *  @param  seqKey The tag key of the sequence to be read
+     *  @param  destination The destination container to read into
+     *  @param  rule The rule (for the sequence) used for reading.
+     *  @return EC_Normal if successful, an error code otherwise.  If the rule
+     *          equlas NULL, then nothing is read at all and an error is returned
+     *          (IOD_EC_NoSuchRule), but no error is reported to the logger.
+     */
+    template <class Container>
+    static OFCondition
+    readSingleItem(DcmItem& source, const DcmTagKey& seqKey, Container& destination, IODRule* rule = NULL)
     {
-      DCMIOD_DEBUG("Will not read sequence " << seqKey << ": No rule supplied");
-      return IOD_EC_NoSuchRule;
+        if (rule == NULL)
+        {
+            DCMIOD_DEBUG("Will not read sequence " << seqKey << ": No rule supplied");
+            return IOD_EC_NoSuchRule;
+        }
+
+        return readSingleItem(source, seqKey, destination, rule->getType(), rule->getModule());
     }
 
-    return readSingleItem(source, seqKey, destination, rule->getType(), rule->getModule());
-  }
-
-  /** Write given container into a DICOM sequence that is created within the
-   *  given item. The sequence is created from scratch, i.e.\ any old sequence
-   *  (and its items) will be overwritten.
-   *  @param  result If writing is successful, result will contain EC_Normal.
-   *          Otherwise an error code is set.
-   *  @param  seqKey The tag key of the sequence to be write
-   *  @param  source The source container to read from. Must support the
-   *          write(DcmItem*) function.
-   *  @param  destination The DICOM destination item to write the sequence to
-   *          See DcmElement::checkVM() for a list of valid values.
-   *  @param  cardinality  Expected number of items (i.e.\ expected number of
-   *          elements in source container). See DcmElement::checkVM() for a
-   *          list of valid values.
-   *  @param  type The sequence type as noted in part 3 of the DICOM standard,
-   *          i.e.\ "1,1C,2,2C or 3".
-   *  @param  module Name of the module/macro this sequence is contained in. Used
-   *                 for error messages and can also be left empty.
-   */
-  template <class Container>
-  static void writeSubSequence(OFCondition& result,
-                               const DcmTagKey& seqKey,
-                               Container& source,
-                               DcmItem& destination,
-                               const OFString& cardinality,
-                               const OFString& type,
-                               const OFString& module)
-  {
-    if ( result.good() )
+    /** Write given container into a DICOM sequence that is created within the
+     *  given item. The sequence is created from scratch, i.e.\ any old sequence
+     *  (and its items) will be overwritten.
+     *  @param  result If writing is successful, result will contain EC_Normal.
+     *          Otherwise an error code is set.
+     *  @param  seqKey The tag key of the sequence to be write
+     *  @param  source The source container to read from. Must support the
+     *          write(DcmItem*) function.
+     *  @param  destination The DICOM destination item to write the sequence to
+     *  @param  cardinality  Expected number of items (i.e.\ expected number of
+     *          elements in source container). See DcmElement::checkVM() for a
+     *          list of valid values.
+     *  @param  type The sequence type as noted in part 3 of the DICOM standard,
+     *          i.e.\ "1,1C,2,2C or 3".
+     *  @param  module Name of the module/macro this sequence is contained in. Used
+     *                 for error messages and can also be left empty.
+     */
+    template <class Container>
+    static void writeSubSequence(OFCondition& result,
+                                 const DcmTagKey& seqKey,
+                                 Container& source,
+                                 DcmItem& destination,
+                                 const OFString& cardinality,
+                                 const OFString& type,
+                                 const OFString& module)
     {
-      // Delete old data
-      destination.findAndDeleteElement(seqKey);
-
-      // If we have meaningful data, write it
-      OFBool haveData = source.size() > 0;
-      if (haveData)
-      {
-        destination.insertEmptyElement(seqKey);
-        Uint32 count = 0;
-        typename Container::iterator it = source.begin();
-        while ( it != source.end() && result.good() )
+        if (result.good())
         {
-          if ( (*it) != NULL)
-          {
-            DcmItem *localItem = NULL;
-            // If item is NULL result.bad() is always true.
-            result = destination.findOrCreateSequenceItem(seqKey, localItem, -2 /* append new */);
-            if ( result.good() )
+            // Delete old data
+            destination.findAndDeleteElement(seqKey);
+
+            // If we have meaningful data, write it
+            OFBool haveData = source.size() > 0;
+            if (haveData)
             {
-              result = (*it)->write(*localItem);
-              if ( result.bad() )
-              {
-                  destination.findAndDeleteSequenceItem(seqKey, -1 /* last */);
-                  DCMIOD_ERROR("Could not write item #" << count << " in " << DcmTag(seqKey).getTagName() << ": " << result.text());
-              }
+                destination.insertEmptyElement(seqKey);
+                Uint32 count                    = 0;
+                typename Container::iterator it = source.begin();
+                while (it != source.end() && result.good())
+                {
+                    if ((*it) != NULL)
+                    {
+                        DcmItem* localItem = NULL;
+                        // If item is NULL result.bad() is always true.
+                        result = destination.findOrCreateSequenceItem(seqKey, localItem, -2 /* append new */);
+                        if (result.good())
+                        {
+                            result = (*it)->write(*localItem);
+                            if (result.bad())
+                            {
+                                destination.findAndDeleteSequenceItem(seqKey, -1 /* last */);
+                                DCMIOD_ERROR("Could not write item #" << count << " in " << DcmTag(seqKey).getTagName()
+                                                                      << ": " << result.text());
+                            }
+                        }
+                        else
+                        {
+                            DCMIOD_ERROR("Could not insert item data #" << count << " of "
+                                                                        << DcmTag(seqKey).getTagName()
+                                                                        << " (internal error), ignoring");
+                        }
+                    }
+                    else
+                    {
+                        DCMIOD_ERROR("Found uninitialized container item (NULL value) for sequence "
+                                     << DcmTag(seqKey).getTagName() << " (internal error, skipping)");
+                    }
+                    count++;
+                    it++;
+                }
             }
-            else
+            // If we do not have data, create empty sequence if type 2
+            else if (type == "2")
+            {
+                destination.insertEmptyElement(seqKey);
+            }
+
+            // Check result
+            checkSubSequence(result, destination, seqKey, cardinality, type, module, dcmtk::log4cplus::ERROR_LOG_LEVEL);
+
+            // Clean up if we did not have success */
+            if (result.bad())
             {
-                DCMIOD_ERROR("Could not insert item data #" << count << " of " << DcmTag(seqKey).getTagName() << " (internal error), ignoring");
+                destination.findAndDeleteElement(seqKey);
             }
-          }
-          else
-          {
-            DCMIOD_ERROR("Found uninitialized container item (NULL value) for sequence " << DcmTag(seqKey).getTagName() << " (internal error, skipping)");
-          }
-          count++;
-          it++;
         }
-      }
-      // If we do not have data, create empty sequence if type 2
-      else if (type == "2")
-      {
-        destination.insertEmptyElement(seqKey);
-      }
-
-      // Check result
-      checkSubSequence(result, destination, seqKey, cardinality, type, module, dcmtk::log4cplus::ERROR_LOG_LEVEL);
-
-      // Clean up if we did not have success */
-      if (result.bad())
-      {
-        destination.findAndDeleteElement(seqKey);
-      }
     }
-  }
-
-  /** Write given container into a DICOM sequence that is created within the given item.
-   *  The container. The sequence is created from scratch, i.e.\ any old sequence
-   *  (and its items) will be overwritten.
-   *  @param  result If writing is successful, result will contain EC_Normal. Otherwise
-   *          an error code is set.
-   *  @param  seqKey The tag key of the sequence to be write
-   *  @param  source The source container to read from. Must support the write(DcmItem*)
-   *          function.
-   *  @param  destination The DICOM destination item to write the sequence to
-   *  @param  rule Rule describing the requirements for this sequence. If NULL
-   *          an error is returned (IOD_EC_NoSuchRule), but no error error is reported
-   *          to the logger.
-   */
-  template <class Container>
-  static void writeSubSequence(OFCondition& result,
-                               const DcmTagKey& seqKey,
-                               Container& source,
-                               DcmItem& destination,
-                               IODRule* rule)
-  {
-    if ( result.good() )
+
+    /** Write given container into a DICOM sequence that is created within the given item.
+     *  The container. The sequence is created from scratch, i.e.\ any old sequence
+     *  (and its items) will be overwritten.
+     *  @param  result If writing is successful, result will contain EC_Normal. Otherwise
+     *          an error code is set.
+     *  @param  seqKey The tag key of the sequence to be write
+     *  @param  source The source container to read from. Must support the write(DcmItem*)
+     *          function.
+     *  @param  destination The DICOM destination item to write the sequence to
+     *  @param  rule Rule describing the requirements for this sequence. If NULL
+     *          an error is returned (IOD_EC_NoSuchRule), but no error error is reported
+     *          to the logger.
+     */
+    template <class Container>
+    static void writeSubSequence(
+        OFCondition& result, const DcmTagKey& seqKey, Container& source, DcmItem& destination, IODRule* rule)
     {
-      if (rule == NULL)
-      {
-        DCMIOD_DEBUG("Will not write sequence " << seqKey << ": No rule supplied");
-        result = IOD_EC_NoSuchRule;
-      }
-      else
-      {
-        writeSubSequence<Container>(result, rule->getTagKey(), source, destination, rule->getVM(), rule->getType(), rule->getModule());
-      }
+        if (result.good())
+        {
+            if (rule == NULL)
+            {
+                DCMIOD_DEBUG("Will not write sequence " << seqKey << ": No rule supplied");
+                result = IOD_EC_NoSuchRule;
+            }
+            else
+            {
+                writeSubSequence<Container>(
+                    result, rule->getTagKey(), source, destination, rule->getVM(), rule->getType(), rule->getModule());
+            }
+        }
     }
-  }
-
-
-  /** Writes given container into a DICOM item of a specific sequence. The
-   *  sequence is created from scratch so that any old information will be lost.
-   *  @param  result If writing is successful, result will contain EC_Normal.
-   *          Otherwise an error code is set.
-   *  @param  seqKey The tag key of the sequence to be written
-   *  @param  source The source container to read from. Must support the write(DcmItem*)
-   *          function.
-   *  @param  destination The DICOM item that should hold the sequence
-   *          (with a single item) in the end.
-   *  @param  type The sequence type as noted in part 3 of the DICOM standard,
-   *          i.e.\ "1,1C,2,2C or 3".
-   *  @param  module Name of the module/macro this sequence is contained in.
-   *          Used for error messages and can also be left empty.
-   */
-  template <class Container>
-  static void writeSingleItem(OFCondition& result,
-                              const DcmTagKey& seqKey,
-                              Container& source,
-                              DcmItem& destination,
-                              const OFString& type,
-                              const OFString& module)
-  {
-    if ( result.good() )
+
+    /** Writes given container into a DICOM item of a specific sequence. The
+     *  sequence is created from scratch so that any old information will be lost.
+     *  @param  result If writing is successful, result will contain EC_Normal.
+     *          Otherwise an error code is set.
+     *  @param  seqKey The tag key of the sequence to be written
+     *  @param  source The source container to read from. Must support the write(DcmItem*)
+     *          function.
+     *  @param  destination The DICOM item that should hold the sequence
+     *          (with a single item) in the end.
+     *  @param  type The sequence type as noted in part 3 of the DICOM standard,
+     *          i.e.\ "1,1C,2,2C or 3".
+     *  @param  module Name of the module/macro this sequence is contained in.
+     *          Used for error messages and can also be left empty.
+     */
+    template <class Container>
+    static void writeSingleItem(OFCondition& result,
+                                const DcmTagKey& seqKey,
+                                Container& source,
+                                DcmItem& destination,
+                                const OFString& type,
+                                const OFString& module)
     {
-      // Delete old data
-      destination.findAndDeleteElement(seqKey);
-
-      /* If we have data, write it */
-      OFCondition haveData = source.check(OFTrue /* Be quiet */);
-      if (haveData.good())
-      {
-        DcmItem *localItem = NULL;
-        // If item is NULL result.bad() is always true.
-        result = destination.findOrCreateSequenceItem(seqKey, localItem, 0);
-        if ( result.good() )
+        if (result.good())
         {
-          result = source.write(*localItem);
-          // It can happen that check() returns OK but no elements have to be
-          // written at all (e.g.\ if it contains only type 3 attributes). In that
-          // case a sequence with a single empty item is written which must be removed
-          // afterwards.
-          if (result.good() && (localItem->card() == 0) )
-          {
+            // Delete old data
             destination.findAndDeleteElement(seqKey);
-          }
+
+            /* If we have data, write it */
+            OFCondition haveData = source.check(OFTrue /* Be quiet */);
+            if (haveData.good())
+            {
+                DcmItem* localItem = NULL;
+                // If item is NULL result.bad() is always true.
+                result = destination.findOrCreateSequenceItem(seqKey, localItem, 0);
+                if (result.good())
+                {
+                    result = source.write(*localItem);
+                    // It can happen that check() returns OK but no elements have to be
+                    // written at all (e.g.\ if it contains only type 3 attributes). In that
+                    // case a sequence with a single empty item is written which must be removed
+                    // afterwards.
+                    if (result.good() && (localItem->card() == 0))
+                    {
+                        destination.findAndDeleteElement(seqKey);
+                    }
+                }
+            }
+            /* If we do not have data, insert empty for type 2 */
+            else if (type == "2")
+            {
+                destination.insertEmptyElement(seqKey);
+            }
+            else if (type == "1C")
+            {
+                DCMIOD_TRACE("Skipping type 1C sequence " << seqKey << ": No data or incomplete data available");
+            }
+            else if (type == "3")
+            {
+                DCMIOD_TRACE("Skipping type 3 sequence " << seqKey << ": No data or incomplete data available");
+            }
+            /* Check outcome */
+            checkSubSequence(result, destination, seqKey, "1", type, module, dcmtk::log4cplus::ERROR_LOG_LEVEL);
         }
-      }
-      /* If we do not have data, insert empty for type 2 */
-      else if (type == "2")
-      {
-        destination.insertEmptyElement(seqKey);
-      }
-      else if (type == "1C")
-      {
-        DCMIOD_TRACE("Skipping type 1C sequence " << seqKey << ": No data or incomplete data available");
-      }
-      else if (type  == "3")
-      {
-        DCMIOD_TRACE("Skipping type 3 sequence " << seqKey << ": No data or incomplete data available");
-      }
-      /* Check outcome */
-      checkSubSequence(result, destination, seqKey, "1", type, module, dcmtk::log4cplus::ERROR_LOG_LEVEL);
     }
-  }
-
-  /** Writes given container into a DICOM item of a specific sequence.
-   *  The sequence is created from scratch so that any old information
-   *  will be lost.
-   *  @param  result If writing is successful, result will contain EC_Normal.
-   *          Otherwise an error code is set.
-   *  @param  seqKey The tag key of the sequence to be written
-   *  @param  source The source container to read from. Must support the
-   *          write(DcmItem*) function.
-   *  @param  destination The DICOM item that should hold the sequence
-   *          (with a single item) in the end.
-   *  @param  rule The rule for writing the given sequence
-   */
-  template <class Container>
-  static void writeSingleItem(OFCondition& result,
-                              const DcmTagKey& seqKey,
-                              Container& source,
-                              DcmItem& destination,
-                              IODRule *rule)
-  {
-    if (result.good())
+
+    /** Writes given container into a DICOM item of a specific sequence.
+     *  The sequence is created from scratch so that any old information
+     *  will be lost.
+     *  @param  result If writing is successful, result will contain EC_Normal.
+     *          Otherwise an error code is set.
+     *  @param  seqKey The tag key of the sequence to be written
+     *  @param  source The source container to read from. Must support the
+     *          write(DcmItem*) function.
+     *  @param  destination The DICOM item that should hold the sequence
+     *          (with a single item) in the end.
+     *  @param  rule The rule for writing the given sequence
+     */
+    template <class Container>
+    static void writeSingleItem(
+        OFCondition& result, const DcmTagKey& seqKey, Container& source, DcmItem& destination, IODRule* rule)
     {
-      if (rule == NULL)
-      {
-        DCMIOD_ERROR("Cannot write sequence " << seqKey << " (no rule supplied)");
-        result = EC_CannotCheck;
-      }
-      else
-      {
-        writeSingleItem(result, seqKey, source, destination, rule->getType(), rule->getModule());
-      }
+        if (result.good())
+        {
+            if (rule == NULL)
+            {
+                DCMIOD_ERROR("Cannot write sequence " << seqKey << " (no rule supplied)");
+                result = EC_CannotCheck;
+            }
+            else
+            {
+                writeSingleItem(result, seqKey, source, destination, rule->getType(), rule->getModule());
+            }
+        }
     }
-  }
-
-
-  /** Check whether a given sequence exists in a given item and whether it conforms to
-   *  to its requirement type
-   *  @param  result If sequence is valid, result is set to EC_Normal, otherwise
-   *          to an error.
-   *  @param  surroundingItem The item that should contain the given sequence.
-   *  @param  seqKey The sequence to look for
-   *  @param  cardinality Expected number of items (i.e.\ expected number of
-   *          elements in source container). See DcmElement::checkVM() for a
-   *          list of valid values.
-   *  @param  type The sequence type as noted in part 3 of the DICOM standard,
-   *          i.e.\ "1,1C,2,2C or 3".
-   *  @param  module Name of the module/macro this sequence is contained in.
-   *          Used for error messages and can also be left empty.
-   *  @param  logLevel The log level to write errors to
-   */
-  static void checkSubSequence(OFCondition& result,
-                               DcmItem& surroundingItem,
-                               const DcmTagKey& seqKey,
-                               const OFString& cardinality,
-                               const OFString& type,
-                               const OFString& module,
-                               const dcmtk::log4cplus::LogLevel logLevel);
-
-  /** Deletes all elements from given container and calls "delete" on each
-   *  of them to clear memory.
-   *  @param container  The container that should be cleared. Must contain
-   *         pointers to objects that are allocated on the heap.
-   */
-  template<class Container>
-  static void freeContainer(Container& container)
-  {
-    typename Container::iterator it = container.begin();
-    while (it != container.end())
+
+    /** Check whether a given sequence exists in a given item and whether it conforms to
+     *  to its requirement type
+     *  @param  result If sequence is valid, result is set to EC_Normal, otherwise
+     *          to an error.
+     *  @param  surroundingItem The item that should contain the given sequence.
+     *  @param  seqKey The sequence to look for
+     *  @param  cardinality Expected number of items (i.e.\ expected number of
+     *          elements in source container). See DcmElement::checkVM() for a
+     *          list of valid values.
+     *  @param  type The sequence type as noted in part 3 of the DICOM standard,
+     *          i.e.\ "1,1C,2,2C or 3".
+     *  @param  module Name of the module/macro this sequence is contained in.
+     *          Used for error messages and can also be left empty.
+     *  @param  logLevel The log level to write errors to
+     */
+    static void checkSubSequence(OFCondition& result,
+                                 DcmItem& surroundingItem,
+                                 const DcmTagKey& seqKey,
+                                 const OFString& cardinality,
+                                 const OFString& type,
+                                 const OFString& module,
+                                 const dcmtk::log4cplus::LogLevel logLevel);
+
+    /** Deletes all elements from given container and calls "delete" on each
+     *  of them to clear memory.
+     *  @param container  The container that should be cleared. Must contain
+     *         pointers to objects that are allocated on the heap.
+     */
+    template <class Container>
+    static void freeContainer(Container& container)
     {
-      delete *it;
-      it++;
+        typename Container::iterator it = container.begin();
+        while (it != container.end())
+        {
+            delete *it;
+            it++;
+        }
+        container.clear();
     }
-    container.clear();
-  }
-
-  /** Clones and copies all elements from source to destination container by
-   *  copy constructing all elements.
-   *  @param src  The container that should be copied. Must contain pointers
-   *         to objects that are allocated on the heap, and that are
-   *         copy-constructible
-   *  @param dst  The container to copy the cloned elements to.
-   */
-  template<class Container>
-  static void copyContainer(const Container& src, Container& dst)
-  {
-    typedef typename OFremove_pointer<typename Container::value_type>::type Element;
-    typename Container::const_iterator it = src.begin();
-    while (it != src.end())
+
+    /** Clones and copies all elements from source to destination container by
+     *  copy constructing all elements.
+     *  If copying fails (because memory is exhausted), EC_MemoryExhausted is returned
+     *  and the destination container is returned empty, i.e. all temporary copies
+     *  of its elements are freed and removed from the container.
+     *  @param  src  The container that should be copied. Must contain pointers
+     *          to objects that are allocated on the heap, and that are
+     *          copy-constructible
+     *  @param  dst  The container to copy the cloned elements to.
+     *  @return EC_Normal if successful, error otherwise
+     */
+    template <class Container>
+    static OFCondition copyContainer(const Container& src, Container& dst)
     {
-      if (*it != NULL)
-      {
-        Element *elem = new Element(**it);
-        dst.push_back ( elem );
-      }
-      else
-      {
-        DCMIOD_ERROR("Could not copy element while copying container: Element is NULL, skipping");
-      }
-      it++;
+        typedef typename OFremove_pointer<typename Container::value_type>::type Element;
+        typename Container::const_iterator it = src.begin();
+        while (it != src.end())
+        {
+            if (*it != NULL)
+            {
+                Element* elem = new Element(**it);
+                if (elem == NULL)
+                {
+                    freeContainer(dst);
+                    return EC_MemoryExhausted;
+                }
+                dst.push_back(elem);
+            }
+            else
+            {
+                DCMIOD_ERROR("Could not copy element while copying container: Element in source is NULL, skipping");
+            }
+            it++;
+        }
+        return EC_Normal;
     }
-  }
-
-
-  template <typename ModuleType>
-  static OFCondition setContentDateAndTimeNow(ModuleType& module)
-  {
-    OFDate date;
-    date.setCurrentDate();
-    OFString tempstr;
-    date.getISOFormattedDate(tempstr, OFFalse /* no delimiters */);
-    OFCondition result = module.setContentDate(tempstr);
-    if (result.good())
+
+    /** Compares all elements in source and destination container by
+     *  using their respective compare(const Container& rhs) method.
+     *  If the number or elements in the Containers are different, the
+     *  containers are not considered equal.
+     *  @param src  The first container
+     *  @param dst  The second container
+     *  @return Zero if containers are equal, other number otherwise
+     */
+    template <class Container>
+    static int compareContainer(const Container& src, const Container& dst)
     {
-      OFTime time;
-      time.setCurrentTime();
-      time.getISOFormattedTime(tempstr, OFTrue /* include seconds */, OFFalse, OFFalse, OFFalse);
-      result = module.setContentTime(tempstr);
+        size_t card = src.size();
+        if (card != dst.size())
+            return -1;
+        typename Container::const_iterator it  = src.begin();
+        typename Container::const_iterator it2 = dst.begin();
+        while (it != src.end())
+        {
+            if ((*it)->compare(**it2) != 0)
+                return 1;
+            it++;
+            it2++;
+        }
+        return 0;
     }
-    return result;
-  }
-
-
-  /** Function that takes a string representation of a tag key and
-   *  converts it to a tag key instance if possible
-   *  @param  keyString String of the format "(gggg,eeee)"
-   *  @return The tag key if it could be parsed, DCM_UndefinedTagKey is returned
-   *          instead (0xffff,0xffff)
-   */
-  static const DcmTagKey parseTagKey(const OFString& keyString);
-
-  /** Decompress given dataset if possible. Decompression codecs have to be
-   *  registered beforehand.
-   *  @param  dset The dataset to decompress
-   *  @return EC_Normal if decompression works, error otherwise
-   */
-  static OFCondition decompress(DcmDataset& dset);
-
-  /** Create new Unique Identifier (UID)
-    *  @param  level 0: instance level, 1: Series level, >=2: Study level.
-    *          Calling always with level=0 is not an error but will result
-    *          in unique values, too.
-    *  @return The UID created.
-    */
-  static OFString createUID(const Uint8 level = 0);
-
-  /** Print warning if more than 2147483647 frames are present. This is the maximum
-   *  number since the Number of Frames attribute has a VR of IS which allows
-   *  a maximum of 2^31-1.
-   *  The method returns the number of frames that can be used, i.e. either
-   *  2147483647 if the maximum is exceeded, otherwise the actual number
-   *  of frames.
-   *  @param  numFramesPresent The number of frames actually present
-   *  @param  warning The message to be printed if Number of Frames
-   *          is larger than 2147483647.
-   *  @return Number of frames that can be safely used.
-   */
-  static Uint32 limitMaxFrames(const size_t numFramesPresent,
-                               const OFString& warning);
 
-private:
+    template <typename ModuleType>
+    static OFCondition setContentDateAndTimeNow(ModuleType& module)
+    {
+        OFDate date;
+        date.setCurrentDate();
+        OFString tempstr;
+        date.getISOFormattedDate(tempstr, OFFalse /* no delimiters */);
+        OFCondition result = module.setContentDate(tempstr);
+        if (result.good())
+        {
+            OFTime time;
+            time.setCurrentTime();
+            time.getISOFormattedTime(tempstr, OFTrue /* include seconds */, OFFalse, OFFalse, OFFalse);
+            result = module.setContentTime(tempstr);
+        }
+        return result;
+    }
 
-  // We only have static functions so we do not need an instance of
-  // this class so far.
+    /** Function that takes a string representation of a tag key and
+     *  converts it to a tag key instance if possible
+     *  @param  keyString String of the format "(gggg,eeee)"
+     *  @return The tag key if it could be parsed, DCM_UndefinedTagKey is returned
+     *          instead (0xffff,0xffff)
+     */
+    static const DcmTagKey parseTagKey(const OFString& keyString);
+
+    /** Decompress given dataset if possible. Decompression codecs have to be
+     *  registered beforehand.
+     *  @param  dset The dataset to decompress
+     *  @return EC_Normal if decompression works, error otherwise
+     */
+    static OFCondition decompress(DcmDataset& dset);
+
+    /** Create new Unique Identifier (UID)
+     *  @param  level 0: instance level, 1: Series level, >=2: Study level.
+     *          Calling always with level=0 is not an error but will result
+     *          in unique values, too.
+     *  @return The UID created.
+     */
+    static OFString createUID(const Uint8 level = 0);
+
+    /** Print warning if more than 2147483647 frames are present. This is the maximum
+     *  number since the Number of Frames attribute has a VR of IS which allows
+     *  a maximum of 2^31-1.
+     *  The method returns the number of frames that can be used, i.e. either
+     *  2147483647 if the maximum is exceeded, otherwise the actual number
+     *  of frames.
+     *  @param  numFramesPresent The number of frames actually present
+     *  @param  warning The message to be printed if Number of Frames
+     *          is larger than 2147483647.
+     *  @return Number of frames that can be safely used.
+     */
+    static Uint32 limitMaxFrames(const size_t numFramesPresent, const OFString& warning);
+
+    /** Extracts Frame structures from the given pixel data element. Only
+     *  applicable for pixel data with Bits Allocated = 1. Within the pixel data element, all
+     *  frames are packed next to each other, with the end of one frame and the
+     *  beginning of the next frame packed bit by bit next to each other. The
+     *  resulting Frames are a bit-by-bit copy of their original counterpart.
+     *  However, their first bit is aligned to the first bit/byte in the Frame,
+     *  and the unused bits in the last byte (if any) are zeroed out.
+     *  @param  pixData The pixel data to read from
+     *  @param  numFrames The number of frames to read
+     *  @param  bitsPerFrame The number of bits per frame (usually rows * columns)
+     *  @param  results The resulting frames. Memory for the frames is allocated
+     *          by the method, so the Vector can/should be empty before calling.
+     *  @result Return EC_Normal on success, error otherwise
+     */
+    static OFCondition extractBinaryFrames(Uint8* pixData,
+                                           const size_t numFrames,
+                                           const size_t bitsPerFrame,
+                                           OFVector<DcmIODTypes::Frame*>& results);
+
+    /** Aligns 1 bit per pixel frame data starting at a given bit position in the
+     *  provided buffer with the start of that buffer. This is used to create
+     *  a frame structure where all the bytes (including the first one) only
+     *  contain data from the frame at hand.
+     *  Note that each byte is filled from the right, i.e. the first pixel will
+     *  represented by the bit at the very right of the first byte, and the 9th
+     *  pixel will be in the very right position of the following byte.
+     *  Example:
+     *    3 bytes input buffer: edcbaZYX mlkjihgf utsrqpon
+     *    Result after aligning 3 bits: fghedcba ponmlkji 000utsrq
+     *    The 000 are unused bits and therefore zeroed out in the last byte. Bits
+     *    ZYX will be shifted out which is ok since it does not belong to the
+     *    current frame. See also dcmseg/tests/tutils.cc for more examples.
+     *  @param  buf The address of the memory buffer to shift
+     *  @param  bufLen The length of the buf memory block in bytes
+     *  @param  numBits The number of bits to shift. Must be 0 <= numBits <= 7.
+     */
+    static void alignFrameOnByteBoundary(Uint8* buf, const size_t bufLen, const Uint8 numBits);
+
+private:
+    // We only have static functions so we do not need an instance of
+    // this class so far.
 
-  /** Undefined default constructor (only static functions)
-   */
-  DcmIODUtil();
+    /** Undefined default constructor (only static functions)
+     */
+    DcmIODUtil();
 
-  /** Undefined destructor
-   */
-  ~DcmIODUtil();
+    /** Undefined destructor
+     */
+    ~DcmIODUtil();
 };
 
 #endif // IODUTIL_H
index 77a34e1d5e1fc2c21eb8507ce7a3618dc71554f9..02d59f6f9da097fd7e81c9fdbea78ed0f9dfd80f 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #include "dcmtk/dcmiod/modbase.h"
 
 /** Class representing the Acquisition Context Module. At the moment
 * only an empty Acquisition Context Sequence is supported, so this
 * class servers more as a placeholder at the moment.
 *
 * Acquisition Context Sequence: (SQ, 1-n, 2)
 *
 */
+ * only an empty Acquisition Context Sequence is supported, so this
+ * class servers more as a placeholder at the moment.
+ *
+ * Acquisition Context Sequence: (SQ, 1-n, 2)
+ *
+ */
 class DCMTK_DCMIOD_EXPORT IODAcquisitionContextModule : public IODModule
 {
 
 public:
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set where this classes rules are added to. If NULL, the
+     *          class creates an empty rule set.
+     */
+    IODAcquisitionContextModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
 
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set where this classes rules are added to. If NULL, the
-   *          class creates an empty rule set.
-   */
-  IODAcquisitionContextModule(OFshared_ptr<DcmItem> item,
-                              OFshared_ptr<IODRules> rules);
+    /** Constructor
+     */
+    IODAcquisitionContextModule();
 
-  /** Constructor
-   */
-  IODAcquisitionContextModule();
+    /** Destructor
+     */
+    virtual ~IODAcquisitionContextModule();
 
-  /** Destructor
-   */
-  virtual ~IODAcquisitionContextModule();
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
 
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of module ("AcquisitionContextModule")
-   *  @return Name of the module ("AcquisitionContextModule")
-   */
-  virtual OFString getName() const;
+    /** Get name of module ("AcquisitionContextModule")
+     *  @return Name of the module ("AcquisitionContextModule")
+     */
+    virtual OFString getName() const;
 
 private:
-
-  /// The name of this module ("AcquisitionContextModule")
-  static const OFString m_ModuleName;
+    /// The name of this module ("AcquisitionContextModule")
+    static const OFString m_ModuleName;
 };
 
 #endif // MODACQUISITIONCONTEXT_H
index 2270c1776452873a2b6e983d75eea2fd8c80d994..36d49b4461a9fa7289b687f00928a8b8357ac0a3 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define MODBASE_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofmem.h"
-#include "dcmtk/ofstd/ofvector.h"
 #include "dcmtk/dcmdata/dcitem.h"
 #include "dcmtk/dcmiod/ioddef.h"
 #include "dcmtk/dcmiod/iodrules.h"
+#include "dcmtk/ofstd/ofmem.h"
+#include "dcmtk/ofstd/ofvector.h"
 
 /** Class for managing sets of dicom attributes (e.g.\ macros and modules).
  *  The data is hold in a container (DcmItem) that can be shared with other
@@ -48,166 +48,153 @@ class DCMTK_DCMIOD_EXPORT IODComponent
 {
 
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          an empty rule set.
-   *  @param  parent The parent of the IOD component (NULL if none or unknown)
-   */
-  IODComponent(OFshared_ptr<DcmItem> item,
-               OFshared_ptr<IODRules> rules,
-               IODComponent* parent = NULL);
-
-  /** Constructor, creates rules and item from scratch.
-   *  @param  parent The parent of the IOD component (NULL if none or unknown)
-   */
-  IODComponent(IODComponent* parent = NULL);
-
-  /** Assignment operator, copies contained item and rule set from rhs to
-   *  "this" attribute set. Performs deep copy, i.e.\ the contained item
-   *  and the rule set are copied. The parent component is set to NULL.
-   *  @param  rhs The IODComponent to be assigned
-   *  @return Reference to this module
-   */
-  IODComponent& operator=(const IODComponent& rhs);
-
-  /** Copy constructor, copies reference to contained item and
-   *  rule set to "this" attribute set.
-   *  @param  rhs The component to be assigned
-   */
-  IODComponent(const IODComponent& rhs);
-
-  /** Virtual Destructor
-   */
-  virtual ~IODComponent();
-
-  /** Clear all attributes from the data that are handled by this module.
-   *  An attribute is considered belonging to the module if there are rules
-   *  marked as belonging to this module via the rule's module name.
-   */
-  void clearData();
-
-  /** Set missing values by inventing "default values". Automatically
-   *  called during write() in IODComponent; does nothing in this base
-   *  class implementation but can be overwritten by derived classes if
-   *  default values are desired.
-   */
-  virtual void inventMissing();
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules() =0;
-
-  /** Get rules handled by this module
-   *  @return The rules
-   */
-  OFshared_ptr<IODRules> getRules()
-  {
-    return m_Rules;
-  }
-
-  /** Make component optional by turning all attributes requirement types of it
-   *  to type 3. In order to reset to the attribute's original types,
-   *  resetRules() can be used.
-   */
-  virtual void makeOptional();
-
-  /** Get name of component
-   *  @return Name of the module
-   */
-  virtual OFString getName() const =0;
-
-  /** Get the data handled by this module
-   *  @return The item containing the data of this module
-   */
-  DcmItem& getData()
-  {
-    return *m_Item;
-  }
-
-  /** Read attributes from given item into this class
-   *  @param source  The source to read from
-   *  @param clearOldData If OFTrue, old data is cleared before reading. Otherwise
-   *         old data is overwritten (or amended)
-   *  @result EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write attributes from this class into given item
-   *  @param  destination The item to write to
-   *  @result EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& destination);
-
-  /** Check whether this component's data satisfies the underlying
-   *  rules
-   *  @param  quiet If OFTrue, not error / warning messages will be produced. Only
-   *                the returned error code will indicate error or OK. Per default,
-   *                logging output is produced (OFFalse).
-   *  @result EC_Normal if rules are satisfied, error otherwise
-   */
-  virtual OFCondition check(const OFBool quiet = OFFalse);
-
-  /** Comparison operator for IOD Components
-   *  @param  rhs The right hand side of the comparison
-   *  @return 0, if the given object is equal to this object, other value otherwise
-   */
-  virtual int compare(const IODComponent& rhs) const;
-
-  /** Static helper function that reads attributes from given
-   *  item into destination item, as determined by the provided
-   *  rules and component name. The rules are only applied when reading
-   *  from the source (which may result in warning messages on the logger),
-   *  but if they could be found they are taken over into the destination
-   *  item no matter whether the element validates against the rule.
-   *  @param  source The item to read from
-   *  @param  rules  The rules that provide the attributes and requirements
-   *          for these attributes
-   *  @param  destination The destination to write to
-   *  @param  componentName The name of the module/component to write
-   *  @result EC_Normal if reading was successful, error otherwise
-   */
-  static OFCondition  read(DcmItem& source,
-                           IODRules& rules,
-                           DcmItem& destination,
-                           const OFString& componentName);
-
-  /** Static helper function that writes attributes from given
-   *  item into destination item, as determined by the provided
-   *  rules and component name. The rules are only applied when writing
-   *  to the destination (which may result in warning messages on the logger,
-   *  and the whole call returning with an error). During reading from the
-   *  source item the elements read are not validated against the rules.
-   *  @param  source The item to read from
-   *  @param  rules  The rules that provide the attributes and requirements
-   *          for these attributes
-   *  @param  destination The destination to write to
-   *  @param  componentName The name of the module/component to write
-   *  @result EC_Normal if reading was successful, error otherwise
-   */
-  static OFCondition write(DcmItem& source,
-                           IODRules& rules,
-                           DcmItem& destination,
-                           const OFString& componentName);
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          an empty rule set.
+     *  @param  parent The parent of the IOD component (NULL if none or unknown)
+     */
+    IODComponent(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules, IODComponent* parent = NULL);
+
+    /** Constructor, creates rules and item from scratch.
+     *  @param  parent The parent of the IOD component (NULL if none or unknown)
+     */
+    IODComponent(IODComponent* parent = NULL);
+
+    /** Assignment operator, copies contained item and rule set from rhs to
+     *  "this" attribute set. Performs deep copy, i.e.\ the contained item
+     *  and the rule set are copied. The parent component is set to NULL.
+     *  @param  rhs The IODComponent to be assigned
+     *  @return Reference to this module
+     */
+    IODComponent& operator=(const IODComponent& rhs);
+
+    /** Copy constructor, copies reference to contained item and
+     *  rule set to "this" attribute set.
+     *  @param  rhs The component to be assigned
+     */
+    IODComponent(const IODComponent& rhs);
+
+    /** Virtual Destructor
+     */
+    virtual ~IODComponent();
+
+    /** Clear all attributes from the data that are handled by this module.
+     *  An attribute is considered belonging to the module if there are rules
+     *  marked as belonging to this module via the rule's module name.
+     */
+    void clearData();
+
+    /** Set missing values by inventing "default values". Automatically
+     *  called during write() in IODComponent; does nothing in this base
+     *  class implementation but can be overwritten by derived classes if
+     *  default values are desired.
+     */
+    virtual void inventMissing();
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules() = 0;
+
+    /** Get rules handled by this module
+     *  @return The rules
+     */
+    OFshared_ptr<IODRules> getRules()
+    {
+        return m_Rules;
+    }
+
+    /** Make component optional by turning all attributes requirement types of it
+     *  to type 3. In order to reset to the attribute's original types,
+     *  resetRules() can be used.
+     */
+    virtual void makeOptional();
+
+    /** Get name of component
+     *  @return Name of the module
+     */
+    virtual OFString getName() const = 0;
+
+    /** Get the data handled by this module
+     *  @return The item containing the data of this module
+     */
+    DcmItem& getData()
+    {
+        return *m_Item;
+    }
+
+    /** Read attributes from given item into this class
+     *  @param source  The source to read from
+     *  @param clearOldData If OFTrue, old data is cleared before reading. Otherwise
+     *         old data is overwritten (or amended)
+     *  @result EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write attributes from this class into given item
+     *  @param  destination The item to write to
+     *  @result EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& destination);
+
+    /** Check whether this component's data satisfies the underlying
+     *  rules
+     *  @param  quiet If OFTrue, not error / warning messages will be produced. Only
+     *                the returned error code will indicate error or OK. Per default,
+     *                logging output is produced (OFFalse).
+     *  @result EC_Normal if rules are satisfied, error otherwise
+     */
+    virtual OFCondition check(const OFBool quiet = OFFalse);
+
+    /** Comparison operator for IOD Components
+     *  @param  rhs The right hand side of the comparison
+     *  @return 0, if the given object is equal to this object, other value otherwise
+     */
+    virtual int compare(const IODComponent& rhs) const;
+
+    /** Static helper function that reads attributes from given
+     *  item into destination item, as determined by the provided
+     *  rules and component name. The rules are only applied when reading
+     *  from the source (which may result in warning messages on the logger),
+     *  but if they could be found they are taken over into the destination
+     *  item no matter whether the element validates against the rule.
+     *  @param  source The item to read from
+     *  @param  rules  The rules that provide the attributes and requirements
+     *          for these attributes
+     *  @param  destination The destination to write to
+     *  @param  componentName The name of the module/component to write
+     *  @result EC_Normal if reading was successful, error otherwise
+     */
+    static OFCondition read(DcmItem& source, IODRules& rules, DcmItem& destination, const OFString& componentName);
+
+    /** Static helper function that writes attributes from given
+     *  item into destination item, as determined by the provided
+     *  rules and component name. The rules are only applied when writing
+     *  to the destination (which may result in warning messages on the logger,
+     *  and the whole call returning with an error). During reading from the
+     *  source item the elements read are not validated against the rules.
+     *  @param  source The item to read from
+     *  @param  rules  The rules that provide the attributes and requirements
+     *          for these attributes
+     *  @param  destination The destination to write to
+     *  @param  componentName The name of the module/component to write
+     *  @result EC_Normal if reading was successful, error otherwise
+     */
+    static OFCondition write(DcmItem& source, IODRules& rules, DcmItem& destination, const OFString& componentName);
 
 protected:
+    /// Shared pointer to the data handled by this class. The item may contain
+    /// more attributes than this class is actually responsible for
+    OFshared_ptr<DcmItem> m_Item;
 
-  /// Shared pointer to the data handled by this class. The item may contain
-  /// more attributes than this class is actually responsible for
-  OFshared_ptr<DcmItem> m_Item;
-
-  /// Rules describing the attributes governed by this class
-  OFshared_ptr<IODRules> m_Rules;
-
-  /// The parent component (may be NULL) of this class
-  IODComponent* m_Parent;
+    /// Rules describing the attributes governed by this class
+    OFshared_ptr<IODRules> m_Rules;
 
+    /// The parent component (may be NULL) of this class
+    IODComponent* m_Parent;
 };
 
-
 /** The class IODModule is an IODComponent without parent component since
  *  a module does always belong to the top level dataset.
  *  Also, different from IODComponents, modules usually share data and
@@ -218,38 +205,35 @@ protected:
 class DCMTK_DCMIOD_EXPORT IODModule : public IODComponent
 {
 public:
-
-  /** Constructor. Similar to the one of IODComponent but no parent
-   *  can be defined since a module is always at top level.
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          an empty rule set.
-   */
-  IODModule(OFshared_ptr<DcmItem> item,
-            OFshared_ptr<IODRules> rules);
-
-  /** Constructor. Creates new empty data container and new empty
-   *  ruleset. No parent component is defined (since a module is always
-   *  on top level.
-   */
-  IODModule();
-
-  /** Copy constructor, creates shallow copy
-   *  @param  rhs The module to copy from
-   */
-  IODModule(const IODModule& rhs);
-
-  /** Assignment operator, creates shallow copy
-   *  @param  rhs The module to copy from
-   *  @return Returns reference to this object
-   */
-  IODModule& operator=(const IODModule& rhs);
-
-  /** Desctructor
-   */
-  ~IODModule() {};
+    /** Constructor. Similar to the one of IODComponent but no parent
+     *  can be defined since a module is always at top level.
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          an empty rule set.
+     */
+    IODModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
+
+    /** Constructor. Creates new empty data container and new empty
+     *  ruleset. No parent component is defined (since a module is always
+     *  on top level.
+     */
+    IODModule();
+
+    /** Copy constructor, creates shallow copy
+     *  @param  rhs The module to copy from
+     */
+    IODModule(const IODModule& rhs);
+
+    /** Assignment operator, creates shallow copy
+     *  @param  rhs The module to copy from
+     *  @return Returns reference to this object
+     */
+    IODModule& operator=(const IODModule& rhs);
+
+    /** Desctructor
+     */
+    ~IODModule() {};
 };
 
-#endif //MODBASE_H
-
+#endif // MODBASE_H
index 23dccbab3b336d61afef66d34f4c36a1841a073b..2b3c81f03cb6dc91e36a9d6d63639f31431557b9 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2017, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define MODCOMMONINSTANCEREF_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofmem.h"
-#include "dcmtk/ofstd/ofvector.h"
 #include "dcmtk/dcmdata/dctk.h"
-#include "dcmtk/dcmiod/iodrules.h"
-#include "dcmtk/dcmiod/modbase.h"
 #include "dcmtk/dcmiod/iodmacro.h"
 #include "dcmtk/dcmiod/iodreferences.h"
-
+#include "dcmtk/dcmiod/iodrules.h"
+#include "dcmtk/dcmiod/modbase.h"
+#include "dcmtk/ofstd/ofmem.h"
+#include "dcmtk/ofstd/ofvector.h"
 
 /** Class representing the Common Instance Reference Module:
  *
@@ -50,103 +49,97 @@ class DCMTK_DCMIOD_EXPORT IODCommonInstanceReferenceModule : public IODModule
 {
 
 public:
-
-  // Forward declaration (class defined later in this file)
-  class StudiesOtherInstancesItem;
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  IODCommonInstanceReferenceModule(OFshared_ptr<DcmItem> item,
-                                   OFshared_ptr<IODRules> rules);
-
-  /** Constructor
-   */
-  IODCommonInstanceReferenceModule();
-
-  /** Clears all data belonging to this module (rules are kept)
-   */
-  virtual void clearData();
-
-  /** Destructor
-   */
-  virtual ~IODCommonInstanceReferenceModule();
-
-  /** Add references
-   *  @param  references The references to be added
-   *  @param  studyInstanceUID The Study Instance UID of "this" object instance.
-   *          It's used to decide whether the provided instances (with their
-   *          own Study Instance UIDs) will go into the Referenced Series Sequence
-   *          or into the Studies Containing Other Referenced Instances Sequence.
-   *          If it is left empty, then the method tries to find "this" instances
-   *          Study Instance UID in the internal item container which may be shared
-   *          with other modules and thus may already provide the Study Instance
-   *          UID (e.g. via General Study Module).
-   *  @param  clearOldData Delete any old references if OFTrue, otherwise keep them
-   *  @result EC_Normal if successful, error otherwise
-   */
-  virtual size_t addReferences(const IODReferences& references,
-                               const OFString& studyInstanceUID = "",
-                               const OFBool clearOldData = OFTrue);
-
-  /** Read data of this module from given source item
-   *  @param  source The item to read from
-   *  @param  clearOldData If OFTrue, old data is cleared before reading, otherwise
-   *          it is overwriten/amended.
-   *  @result EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write data of this module into given destination item
-   *  @param  destination The item to write to
-   *  @result EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& destination);
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of module ("CommonInstanceReferenceModule")
-   *  @return Name of the module ("CommonInstanceReferenceModule")
-   */
-  virtual OFString getName() const;
-
-  /** Return reference to list of Referenced Series items
-   *  @return Reference to list of Reference Series Items
-   */
-  OFVector<IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem*>& getReferencedSeriesItems();
-
-  /** Return reference to content of Studies Containing Other Referenced Instances Sequence
-   *  @return Reference to content of Studies Containing Other Referenced Instances Sequence
-   */
-  OFVector<StudiesOtherInstancesItem*>& getStudiesContainingOtherReferences();
+    // Forward declaration (class defined later in this file)
+    class StudiesOtherInstancesItem;
+
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     */
+    IODCommonInstanceReferenceModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
+
+    /** Constructor
+     */
+    IODCommonInstanceReferenceModule();
+
+    /** Clears all data belonging to this module (rules are kept)
+     */
+    virtual void clearData();
+
+    /** Destructor
+     */
+    virtual ~IODCommonInstanceReferenceModule();
+
+    /** Add references
+     *  @param  references The references to be added
+     *  @param  studyInstanceUID The Study Instance UID of "this" object instance.
+     *          It's used to decide whether the provided instances (with their
+     *          own Study Instance UIDs) will go into the Referenced Series Sequence
+     *          or into the Studies Containing Other Referenced Instances Sequence.
+     *          If it is left empty, then the method tries to find "this" instances
+     *          Study Instance UID in the internal item container which may be shared
+     *          with other modules and thus may already provide the Study Instance
+     *          UID (e.g. via General Study Module).
+     *  @param  clearOldData Delete any old references if OFTrue, otherwise keep them
+     *  @result EC_Normal if successful, error otherwise
+     */
+    virtual size_t addReferences(const IODReferences& references,
+                                 const OFString& studyInstanceUID = "",
+                                 const OFBool clearOldData        = OFTrue);
+
+    /** Read data of this module from given source item
+     *  @param  source The item to read from
+     *  @param  clearOldData If OFTrue, old data is cleared before reading, otherwise
+     *          it is overwriten/amended.
+     *  @result EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write data of this module into given destination item
+     *  @param  destination The item to write to
+     *  @result EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& destination);
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of module ("CommonInstanceReferenceModule")
+     *  @return Name of the module ("CommonInstanceReferenceModule")
+     */
+    virtual OFString getName() const;
+
+    /** Return reference to list of Referenced Series items
+     *  @return Reference to list of Reference Series Items
+     */
+    OFVector<IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem*>& getReferencedSeriesItems();
+
+    /** Return reference to content of Studies Containing Other Referenced Instances Sequence
+     *  @return Reference to content of Studies Containing Other Referenced Instances Sequence
+     */
+    OFVector<StudiesOtherInstancesItem*>& getStudiesContainingOtherReferences();
 
 protected:
-
-  virtual OFCondition addSeriesReference(
-    OFVector<IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem*>& container,
-    const IODReference& ref);
+    virtual OFCondition
+    addSeriesReference(OFVector<IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem*>& container,
+                       const IODReference& ref);
 
 private:
+    void freeMemory();
 
-  void freeMemory();
-
-  /// Vector with all items of the Referenced Series Sequence
-  OFVector<IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem*> m_ReferenceSeriesItems;
+    /// Vector with all items of the Referenced Series Sequence
+    OFVector<IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem*> m_ReferenceSeriesItems;
 
-  /// Name of this component ("CommonInstanceReferenceModule")
-  static const OFString m_ComponentName;
+    /// Name of this component ("CommonInstanceReferenceModule")
+    static const OFString m_ComponentName;
 
-  /// Items of Studies Containing Other Referenced Instances Sequence
-  OFVector<StudiesOtherInstancesItem*> m_StudiesContainingOtherReferencedInstancesSequence;
+    /// Items of Studies Containing Other Referenced Instances Sequence
+    OFVector<StudiesOtherInstancesItem*> m_StudiesContainingOtherReferencedInstancesSequence;
 };
 
-
 /** Class representing items from the Studies Containing Other Referenced Instances Sequence,
  *  as used within the Common Instance Reference Module
  *
@@ -159,86 +152,77 @@ class DCMTK_DCMIOD_EXPORT IODCommonInstanceReferenceModule::StudiesOtherInstance
 {
 
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   *  @param  parent The parent of the IOD component (NULL if none or unknown)
-   */
-  StudiesOtherInstancesItem(OFshared_ptr<DcmItem> item,
-                            OFshared_ptr<IODRules> rules,
-                            IODComponent* parent = NULL);
-
-  /** Constructor
-   *  @param  parent The parent component of this module, might be NULL
-   */
-  StudiesOtherInstancesItem(IODComponent* parent = NULL);
-
-  /** Destructor
-   */
-  virtual ~StudiesOtherInstancesItem();
-
-  /** Clear (removes) all attributes handled by the modules of this component.
-   *  Rules are not reset.
-   */
-  virtual void clearData();
-
-  /** Read data from source item into this module
-   *  @param  source The item to read from
-   *  @param  clearOldData If OFTrue, old data is cleared first, otherwise it is
-   *          overwritten/amended
-   *  @result EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write this module's data into given destination item
-   *  @param  destination Item to write to
-   *  @result EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& destination);
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of module ("StudiesContainingOtherReferencedInstancesSequence")
-   *  @return Name of the module ("StudiesContainingOtherReferencedInstancesSequence")
-   */
-  virtual OFString getName() const;
-
-  /** Get Study Instance UID
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getStudyInstanceUID(OFString &value,
-                                          const signed long pos = 0) const;
-
-  /** Set Study Instance UID
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (PN) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setStudyInstanceUID(const OFString& value,
-                                          const OFBool checkValue = OFTrue);
-
-
-  /** Get Series And Instance Reference Macro
-  *  @return Reference to the Series And Instance Reference Macro structure
-  */
-  virtual IODSeriesAndInstanceReferenceMacro& getReferencedSeriesAndInstanceReferences();
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     *  @param  parent The parent of the IOD component (NULL if none or unknown)
+     */
+    StudiesOtherInstancesItem(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules, IODComponent* parent = NULL);
+
+    /** Constructor
+     *  @param  parent The parent component of this module, might be NULL
+     */
+    StudiesOtherInstancesItem(IODComponent* parent = NULL);
+
+    /** Destructor
+     */
+    virtual ~StudiesOtherInstancesItem();
+
+    /** Clear (removes) all attributes handled by the modules of this component.
+     *  Rules are not reset.
+     */
+    virtual void clearData();
+
+    /** Read data from source item into this module
+     *  @param  source The item to read from
+     *  @param  clearOldData If OFTrue, old data is cleared first, otherwise it is
+     *          overwritten/amended
+     *  @result EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write this module's data into given destination item
+     *  @param  destination Item to write to
+     *  @result EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& destination);
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of module ("StudiesContainingOtherReferencedInstancesSequence")
+     *  @return Name of the module ("StudiesContainingOtherReferencedInstancesSequence")
+     */
+    virtual OFString getName() const;
+
+    /** Get Study Instance UID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getStudyInstanceUID(OFString& value, const signed long pos = 0) const;
+
+    /** Set Study Instance UID
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (PN) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setStudyInstanceUID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Get Series And Instance Reference Macro
+     *  @return Reference to the Series And Instance Reference Macro structure
+     */
+    virtual IODSeriesAndInstanceReferenceMacro& getReferencedSeriesAndInstanceReferences();
 
 private:
+    /// The name of this component ("StudiesContainingOtherReferencedInstancesSequence")
+    static const OFString m_ComponentName;
 
-  /// The name of this component ("StudiesContainingOtherReferencedInstancesSequence")
-  static const OFString m_ComponentName;
-
-  /// The Series and Instance Reference Macro used in this item
-  IODSeriesAndInstanceReferenceMacro m_ReferencedSeriesAndInstance;
+    /// The Series and Instance Reference Macro used in this item
+    IODSeriesAndInstanceReferenceMacro m_ReferencedSeriesAndInstance;
 };
 
-
 #endif // MODCOMMONINSTANCEREF_H
index 7721d3c1c43db16ed9c0eb6c2ff9980b804b104a..a6e5367bad7dacf2f83f5bbc6ce99ade0eaea02d 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -38,60 +38,64 @@ class DCMTK_DCMIOD_EXPORT IODEnhGeneralEquipmentModule : public IODModule
 {
 
 public:
-
     /** Convenient struct containing all information required for setting
      *  enhanced equipment information (for use by external code)
      */
     struct DCMTK_DCMIOD_EXPORT EquipmentInfo
     {
 
-      /** Default Constructor
-       */
-      EquipmentInfo() :
-        m_Manufacturer(),
-        m_ManufacturerModelName(),
-        m_DeviceSerialNumber(),
-        m_SoftwareVersions() {}
-
-      /** Convenience Constructor setting all values
-       *  @param manufacturer Manufacturer
-       *  @param manufacturerModelName Manufacturer's model name
-       *  @param deviceSerialNumber Serial number
-       *  @param softwareVersions Software versions
-       */
-      EquipmentInfo(const OFString& manufacturer,
-                    const OFString& manufacturerModelName,
-                    const OFString& deviceSerialNumber,
-                    const OFString& softwareVersions) :
-        m_Manufacturer(manufacturer),
-        m_ManufacturerModelName(manufacturerModelName),
-        m_DeviceSerialNumber(deviceSerialNumber),
-        m_SoftwareVersions(softwareVersions) {}
-
-      /** Perform simple check whether all equipment data is filled in. Does not
-       *  check VR or VM (will be checked in write() routine, though)
-       *  @return OFTrue if data is complete, OFFalse otherwise
-       */
-      OFBool isDataComplete() const
-      {
-        if (m_Manufacturer.empty() || m_ManufacturerModelName.empty() || m_DeviceSerialNumber.empty() || m_SoftwareVersions.empty())
+        /** Default Constructor
+         */
+        EquipmentInfo()
+            : m_Manufacturer()
+            , m_ManufacturerModelName()
+            , m_DeviceSerialNumber()
+            , m_SoftwareVersions()
         {
-          return OFFalse;
         }
-        return OFTrue;
-      }
 
-      /// Manufacturer (VM 1)
-      OFString m_Manufacturer;
+        /** Convenience Constructor setting all values
+         *  @param manufacturer Manufacturer
+         *  @param manufacturerModelName Manufacturer's model name
+         *  @param deviceSerialNumber Serial number
+         *  @param softwareVersions Software versions
+         */
+        EquipmentInfo(const OFString& manufacturer,
+                      const OFString& manufacturerModelName,
+                      const OFString& deviceSerialNumber,
+                      const OFString& softwareVersions)
+            : m_Manufacturer(manufacturer)
+            , m_ManufacturerModelName(manufacturerModelName)
+            , m_DeviceSerialNumber(deviceSerialNumber)
+            , m_SoftwareVersions(softwareVersions)
+        {
+        }
 
-      /// Manufacturer's Model Name (VM 1)
-      OFString m_ManufacturerModelName;
+        /** Perform simple check whether all equipment data is filled in. Does not
+         *  check VR or VM (will be checked in write() routine, though)
+         *  @return OFTrue if data is complete, OFFalse otherwise
+         */
+        OFBool isDataComplete() const
+        {
+            if (m_Manufacturer.empty() || m_ManufacturerModelName.empty() || m_DeviceSerialNumber.empty()
+                || m_SoftwareVersions.empty())
+            {
+                return OFFalse;
+            }
+            return OFTrue;
+        }
 
-      /// Device Serial Number (VM 1)
-      OFString m_DeviceSerialNumber;
+        /// Manufacturer (VM 1)
+        OFString m_Manufacturer;
 
-      /// Software Version(s) (VM 1-n)
-      OFString m_SoftwareVersions;
+        /// Manufacturer's Model Name (VM 1)
+        OFString m_ManufacturerModelName;
+
+        /// Device Serial Number (VM 1)
+        OFString m_DeviceSerialNumber;
+
+        /// Software Version(s) (VM 1-n)
+        OFString m_SoftwareVersions;
     };
 
     /** Constructor
@@ -100,8 +104,7 @@ public:
      *  @param  rules The rule set for this class. If NULL, the class creates
      *          one from scratch and adds its values.
      */
-    IODEnhGeneralEquipmentModule(OFshared_ptr<DcmItem> item,
-                                 OFshared_ptr<IODRules> rules);
+    IODEnhGeneralEquipmentModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
 
     /** Constructor
      */
@@ -111,8 +114,7 @@ public:
      */
     virtual ~IODEnhGeneralEquipmentModule();
 
-    static OFCondition create(const EquipmentInfo& info,
-                              IODEnhGeneralEquipmentModule* equipment);
+    static OFCondition create(const EquipmentInfo& info, IODEnhGeneralEquipmentModule* equipment);
 
     /** Resets rules to their original values.
      */
@@ -128,64 +130,56 @@ public:
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getManufacturer(OFString &value,
-                                        const signed long pos = 0) const;
+    virtual OFCondition getManufacturer(OFString& value, const signed long pos = 0) const;
 
     /** Get Manufacturer's Model Name
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getManufacturerModelName(OFString &value,
-                                                 const signed long pos = 0) const;
+    virtual OFCondition getManufacturerModelName(OFString& value, const signed long pos = 0) const;
 
     /** Get Device Serial Number
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getDeviceSerialNumber(OFString &value,
-                                              const signed long pos = 0) const;
+    virtual OFCondition getDeviceSerialNumber(OFString& value, const signed long pos = 0) const;
 
     /** Get Software Version(s)
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getSoftwareVersions(OFString &value,
-                                            const signed long pos = 0) const;
+    virtual OFCondition getSoftwareVersions(OFString& value, const signed long pos = 0) const;
 
     /** Set Manufacturer
      *  @param  value Value to be set (single value only) or "" for no value
      *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1) if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setManufacturer(const OFString &value,
-                                        const OFBool checkValue = OFTrue);
+    virtual OFCondition setManufacturer(const OFString& value, const OFBool checkValue = OFTrue);
 
     /** Set Manufacturer's Model Name
      *  @param  value Value to be set (single value only) or "" for no value
      *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1) if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setManufacturerModelName(const OFString &value,
-                                                 const OFBool checkValue = OFTrue);
+    virtual OFCondition setManufacturerModelName(const OFString& value, const OFBool checkValue = OFTrue);
 
     /** Set Device Serial Number
      *  @param  value Value to be set (single value only) or "" for no value
      *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1) if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setDeviceSerialNumber(const OFString &value,
-                                              const OFBool checkValue = OFTrue);
+    virtual OFCondition setDeviceSerialNumber(const OFString& value, const OFBool checkValue = OFTrue);
 
     /** Set Software Version(s)
      *  @param  value Value to be set (possibly multi-valued) or "" for no value
      *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1-n) if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setSoftwareVersions(const OFString &value,
-                                            const OFBool checkValue = OFTrue);
+    virtual OFCondition setSoftwareVersions(const OFString& value, const OFBool checkValue = OFTrue);
 
     /** Set all equipment information at once
      *  @param  info The equipment information to be set.
@@ -194,10 +188,8 @@ public:
     virtual OFCondition set(const EquipmentInfo& info);
 
 private:
-
     /// Name of the module ("EnhancedEquipmentModule")
     OFString m_ModuleName;
 };
 
-
 #endif // MODENHEQUIPMENT_H
index 374019139b81d6a6db03a3c05b45a42b6a396e88..b7293b029111aaddf9d733301dc19acef59939e5 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2020, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -23,8 +23,8 @@
 #define MODENHUSIMAGE_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmiod/modbase.h"
 #include "dcmtk/dcmiod/iodmacro.h"
+#include "dcmtk/dcmiod/modbase.h"
 
 /** Class representing the Enhanced US Image Module:
  *
@@ -67,527 +67,471 @@ class DCMTK_DCMIOD_EXPORT IODEnhUSImageModule : public IODModule
 {
 
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set where this classes rules are added to. If NULL, the
-   *          class creates an empty rule set.
-   */
-  IODEnhUSImageModule(OFshared_ptr<DcmItem> item,
-                      OFshared_ptr<IODRules> rules);
-
-  /** Constructor
-   */
-  IODEnhUSImageModule();
-
-  /** Destructor
-   */
-  virtual ~IODEnhUSImageModule();
-
-  /** Resets rules to their original values.
-   */
-  virtual void resetRules();
-
-  /** Get name of module
-   *  @return Name of the module ("EnhancedUSImageModule")
-   */
-  virtual OFString getName() const;
-
-  /** Read attributes from given item into this class. Overwrites
-   *  fucntion of base class IODComponent.
-   *  @param source  The source to read from
-   *  @param clearOldData If OFTrue, old data is cleared before reading. Otherwise
-   *         old data is overwritten (or amended)
-   *  @result EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write attributes from this class into given item. Overwrites
-   *  function of base class IODComponent.
-   *  @param  destination The item to write to
-   *  @result EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& destination);
-
-  /** Get Image Type
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all values
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getImageType(OFString &value,
-                                   const signed long pos = 0);
-
-  /** Get Samples Per Pixel
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-  */
-  virtual OFCondition getSamplesPerPixel(Uint16& value,
-                                         const unsigned long pos = 0);
-
-  /** Get Photometric Interpretation
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all values
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getPhotometricInterpretation(OFString& value,
-                                                   const signed long pos = 0);
-
-  /** Get Rows
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getRows(Uint16& value,
-                              const unsigned long pos = 0);
-
-  /** Get Columns
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getColumns(Uint16& value,
-                                  const unsigned long pos = 0);
-   /** Get Bits Allocated
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1)
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getBitsAllocated(Uint16& value,
-                                       const unsigned long pos = 0);
-
-   /** Get Bits Stored
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1)
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getBitsStored(Uint16& value,
-                                  const unsigned long pos = 0);
-
-  /** Get High Bit
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getHighBit(Uint16& value,
-                                 const unsigned long pos = 0);
-
-  /** Get Pixel Representation
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getPixelRepresentation(Uint16& value,
-                                             const unsigned long pos = 0);
-
-  /** Get Dimension Organization Type
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all values
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getDimensionOrganizationType(OFString& value,
-                                                   const signed long pos = 0);
-
-  /** Get Acquisition DateTime
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all values
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getAcquisitionDateTime(OFString& value,
-                                             const signed long pos = 0);
-
-  /** Get Acquisition Duration
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getAcquisitionDuration(Float64& value,
-                                             const unsigned long pos = 0);
-
-  /** Get Pixel Spacing
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getPixelSpacing(Float64& value,
-                                      const unsigned long pos = 0);
-
-  /** Get Position Measuring Device
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getPositionMeasuringDevice(OFString& value,
-                                                 const signed long pos = 0);
-
-  /** Get Lossy Image Compression
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all values
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getLossyImageCompression(OFString& value,
-                                               const signed long pos = 0);
-
-  /** Get Lossy Image Compression Ratio
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getLossyImageCompressionRatio(Float64& value,
-                                                    const unsigned long pos = 0);
-
-  /** Get Lossy Image Compression Method
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all values
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getLossyImageCompressionMethod(OFString& value,
-                                                     const signed long pos = 0);
-
-  /** Get Presentation LUT Shape
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all values
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getPresentationLUTShape(OFString& value,
-                                              const signed long pos = 0);
-  /** Get Rescale Slope
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getRescaleSlope(Float64& value,
-                                      const unsigned long pos = 0);
-  /** Get Rescale Intercept
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all values
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getRescaleIntercept(OFString& value,
-                                          const signed long pos = 0);
-
-  /** Get Burned-In Annotation
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all values
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getBurnedInAnnotation(OFString& value,
-                                            const signed long pos = 0);
-  /** Get Recognizable Visual Features
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all values
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getRecognizableVisibleFeatures(OFString& value,
-                                                     const signed long pos = 0);
-  /** Get Mandatory View And Slice Progression Direction
-   *  @return Reference to Mandatory View And Slice Progression Direction
-   */
-  virtual MandatoryViewAndSliceProgressionDirectionMacro& getMandatoryViewAndSliceProgressionDirection();
-
-  /** Get Anatomy
-   *  @return Reference to Anatomy
-   */
-  virtual GeneralAnatomyMacro& getAnatomy();
-
-  /** Get Transducer Scan Pattern
-   *  @return Reference to Transducer Scan Pattern
-   */
-  virtual CodeSequenceMacro& getTransducerScanPattern();
-
-  /** Get Transducer Geometry Code
-   *  @return Reference to Transducer Geometry
-   */
-  virtual CodeSequenceMacro& getTransducerGeometry();
-
-  /** Get Transducer Beam Steering
-   *  @return Reference to Transducer Beam Steering
-   */
-  virtual OFVector<CodeSequenceMacro*>& getTransducerBeamSteering();
-
-  /** Get Transducer Application
-   *  @return Reference to Transducer Application
-   */
-  virtual CodeSequenceMacro& getTransducerApplication();
-
-  /** Get Processing Function
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all values
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getProcessingFunction(OFString& value,
-                                            const signed long pos = 0);
-  /** Get Mechanical Index
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getMechanicalIndex(Float64& value,
-                                         const unsigned long pos = 0);
-
-  /** Get Bone Thermal Index
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getBoneThermalIndex(Float64& value,
-                                          const unsigned long pos = 0);
-
-  /** Get Cranial Thermal Index
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all values
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getCranialThermalIndex(Float64& value,
-                                             const unsigned long pos = 0);
-
-  /** Get Soft Tissue Thermal Index
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all values
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getSoftTissueThermalIndex(Float64& value,
-                                                const unsigned long pos = 0);
-
-  /** Get Depth(s) of Focus
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getDepthsOfFocus(Float64& value,
-                                       const unsigned long pos = 0);
-
-  /** Get Depth(s) of Scan Field
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getDepthsOfScanField(Float64& value,
-                                           const unsigned long pos = 0);
-
-  /** Set Image Type. Image Type contains up to four values. Value 3 and 4 are
-   *  optional and can be left empty if desired. The values in their order
-   *  of occurrence are:
-   *  1) Pixel Data Characteristics: Either ORIGINAL or DERIVED
-   *  2) Patient Examination Characteristics: Fixed to "PRIMARY", thus cannot be
-   *  influenced through this function.
-   *  3) Image Flavor: Defined Terms listed in the standard
-   *  4) Derived Pixel Contrast: Defined Terms listed in the standard
-   *  @param  pixelDataChar Value 1 of Image Type
-   *  @param  imageFlavor Value 3 of Image Type
-   *  @param  derivedPixelContrast Value 4 of Image Type
-   *  @param  checkValue If OFTrue, the value is checked for conformance.
-   *  @return EC_Normal if setting was successful, error otherwise.
-   */
-  virtual OFCondition setImageType(const DcmIODTypes::IOD_ENHUSIMAGETYPE pixelDataChar,
-                                   const OFString& imageFlavor = "",
-                                   const OFString& derivedPixelContrast = "",
-                                   const OFBool checkValue = OFTrue);
-
-  /** Set Rows
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRows(const Uint16 value,
-                              const OFBool checkValue = OFTrue);
-
-  /** Set Columns
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setColumns(const Uint16 value,
-                                 const OFBool checkValue = OFTrue);
-  /** Set Bits Allocated
-   *  @param  value Value to be set, permitted values: 8 or 16
-   *  @param  checkValue Check 'value' for conformance if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setBitsAllocated(const Uint16 value,
-                                       const OFBool checkValue = OFTrue);
-
-  /** Set Bits Stored
-   *  @param  value Value to be set, permitted values: 8 or 16
-   *  @param  checkValue Check 'value' for conformance if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setBitsStored(const Uint16 value,
-                                    const OFBool checkValue = OFTrue);
-
-  /** Set High Bit
-   *  @param  value Value to be set, permitted values: 7 or 15
-   *  @param  checkValue Check 'value' for conformance if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setHighBit(const Uint16 value,
-                                 const OFBool checkValue = OFTrue);
-
-  /** Set Dimension Organization Type
-   *  @param  value Value to be set, permitted values: "3D" or "3D_TEMPORAL"
-   *  @param  checkValue Check 'value' for conformance if enabled, including VR (CS) and VM (1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setDimensionOrganizationType(const OFString& value,
-                                                   const OFBool checkValue = OFTrue);
-
-  /** Set Acquisition DateTime
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance if enabled, including VR (DT) and VM (1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setAcquisitionDateTime(const OFString& value,
-                                             const OFBool checkValue = OFTrue);
-
-  /** Set Acquisition Duration
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance if enabled,
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setAcquisitionDuration(const Float64 value,
-                                             const OFBool checkValue = OFTrue);
-
-  /** Set Pixel Spacing
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance if enabled, including VR (DS) and VM (2)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPixelSpacing(const OFString& value,
-                                      const OFBool checkValue = OFTrue);
-
-  /** Set Position Measuring Device
-   *  @param  value Value to be set, permitted values: "RIGID" or "FREEHAND"
-   *  @param  checkValue Check 'value' for conformance if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPositionMeasuringDevice(const OFString& value,
-                                                 const OFBool checkValue = OFTrue);
-
-  /** Set Lossy Image Compression
-   *  @param  value Value to be set, permitted values: "00" (not lossy compressed) or "01" (lossy compressed)
-   *  @param  checkValue Check 'value' for conformance if enabled, including VR (CS) and VM (1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setLossyImageCompression(const OFString& value,
-                                               const OFBool checkValue = OFTrue);
-
-  /** Set Lossy Image Compression Ratio
-   *  @param  value Value to be set, including VR (DS) and VM (1-n)
-   *  @param  checkValue Check 'value' for conformance if enabled, including VR (DS)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setLossyImageCompressionRatio(const OFString& value,
-                                                    const OFBool checkValue = OFTrue);
-
-  /** Set Lossy Image Compression Method
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance if enabled, including VR (CS)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setLossyImageCompressionMethod(const OFString& value,
-                                                     const OFBool checkValue = OFTrue);
-
-  /** Set Recognizable Visual Features
-   *  @param  value Value to be set, permitted values: "YES" or "NO"
-   *  @param  checkValue Check 'value' for conformance if enabled, including VR (CS) and VM (1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRecognizableVisibleFeatures(const OFString& value,
-                                                     const OFBool checkValue = OFTrue);
-
-  /** Set Processing Funcion
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance if enabled, including VR (LO) and VM (1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setProcessingFunction(const OFString& value,
-                                            const OFBool checkValue = OFTrue);
-
-  /** Set Mechanical Index
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance if enabled, including VR (DS) and VM (1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setMechanicalIndex(const OFString& value,
-                                         const OFBool checkValue = OFTrue);
-
-  /** Set Bone Thermal Index
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance if enabled, including VR (DS) and VM (1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setBoneThermalIndex(const OFString& value,
-                                          const OFBool checkValue = OFTrue);
-
-  /** Set Cranial Thermal Index
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance if enabled, including VR (DS) and VM (1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setCranialThermalIndex(const OFString& value,
-                                             const OFBool checkValue = OFTrue);
-
-  /** Set Soft Tissue Thermal Index
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance if enabled, including VR (DS) and VM (1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSoftTissueThermalIndex(const OFString& value,
-                                                const OFBool checkValue = OFTrue);
-
-  /** Set Depth(s) of Focus
-   *  @param  value Value to be set
-   *  @param  pos Index of the value to set (0..vm-1)
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency with
-   *          other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setDepthsOfFocus(const Float64 value,
-                                       const unsigned long pos,
-                                       const OFBool checkValue = OFTrue);
-
-  /** Set Depth(s) of Focus (convenience function)
-   *  @param  values Value(s) to be set
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency with
-   *          other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setDepthsOfFocus(const OFVector<Float64>& values,
-                                       const OFBool checkValue = OFTrue);
-
-  /** Set Depth(s) of Scan Field
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance if enabled, including VR (IS) and VM (1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setDepthsOfScanField(const OFString& value,
-                                           const OFBool checkValue = OFTrue);
-
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set where this classes rules are added to. If NULL, the
+     *          class creates an empty rule set.
+     */
+    IODEnhUSImageModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
+
+    /** Constructor
+     */
+    IODEnhUSImageModule();
+
+    /** Destructor
+     */
+    virtual ~IODEnhUSImageModule();
+
+    /** Resets rules to their original values.
+     */
+    virtual void resetRules();
+
+    /** Get name of module
+     *  @return Name of the module ("EnhancedUSImageModule")
+     */
+    virtual OFString getName() const;
+
+    /** Read attributes from given item into this class. Overwrites
+     *  fucntion of base class IODComponent.
+     *  @param source  The source to read from
+     *  @param clearOldData If OFTrue, old data is cleared before reading. Otherwise
+     *         old data is overwritten (or amended)
+     *  @result EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write attributes from this class into given item. Overwrites
+     *  function of base class IODComponent.
+     *  @param  destination The item to write to
+     *  @result EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& destination);
+
+    /** Get Image Type
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all values
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getImageType(OFString& value, const signed long pos = 0);
+
+    /** Get Samples Per Pixel
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSamplesPerPixel(Uint16& value, const unsigned long pos = 0);
+
+    /** Get Photometric Interpretation
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all values
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPhotometricInterpretation(OFString& value, const signed long pos = 0);
+
+    /** Get Rows
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getRows(Uint16& value, const unsigned long pos = 0);
+
+    /** Get Columns
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getColumns(Uint16& value, const unsigned long pos = 0);
+    /** Get Bits Allocated
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getBitsAllocated(Uint16& value, const unsigned long pos = 0);
+
+    /** Get Bits Stored
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getBitsStored(Uint16& value, const unsigned long pos = 0);
+
+    /** Get High Bit
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getHighBit(Uint16& value, const unsigned long pos = 0);
+
+    /** Get Pixel Representation
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPixelRepresentation(Uint16& value, const unsigned long pos = 0);
+
+    /** Get Dimension Organization Type
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all values
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getDimensionOrganizationType(OFString& value, const signed long pos = 0);
+
+    /** Get Acquisition DateTime
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all values
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getAcquisitionDateTime(OFString& value, const signed long pos = 0);
+
+    /** Get Acquisition Duration
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getAcquisitionDuration(Float64& value, const unsigned long pos = 0);
+
+    /** Get Pixel Spacing
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPixelSpacing(Float64& value, const unsigned long pos = 0);
+
+    /** Get Position Measuring Device
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPositionMeasuringDevice(OFString& value, const signed long pos = 0);
+
+    /** Get Lossy Image Compression
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all values
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getLossyImageCompression(OFString& value, const signed long pos = 0);
+
+    /** Get Lossy Image Compression Ratio
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getLossyImageCompressionRatio(Float64& value, const unsigned long pos = 0);
+
+    /** Get Lossy Image Compression Method
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all values
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getLossyImageCompressionMethod(OFString& value, const signed long pos = 0);
+
+    /** Get Presentation LUT Shape
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all values
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPresentationLUTShape(OFString& value, const signed long pos = 0);
+    /** Get Rescale Slope
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getRescaleSlope(Float64& value, const unsigned long pos = 0);
+    /** Get Rescale Intercept
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all values
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getRescaleIntercept(OFString& value, const signed long pos = 0);
+
+    /** Get Burned-In Annotation
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all values
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getBurnedInAnnotation(OFString& value, const signed long pos = 0);
+    /** Get Recognizable Visual Features
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all values
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getRecognizableVisibleFeatures(OFString& value, const signed long pos = 0);
+    /** Get Mandatory View And Slice Progression Direction
+     *  @return Reference to Mandatory View And Slice Progression Direction
+     */
+    virtual MandatoryViewAndSliceProgressionDirectionMacro& getMandatoryViewAndSliceProgressionDirection();
+
+    /** Get Anatomy
+     *  @return Reference to Anatomy
+     */
+    virtual GeneralAnatomyMacro& getAnatomy();
+
+    /** Get Transducer Scan Pattern
+     *  @return Reference to Transducer Scan Pattern
+     */
+    virtual CodeSequenceMacro& getTransducerScanPattern();
+
+    /** Get Transducer Geometry Code
+     *  @return Reference to Transducer Geometry
+     */
+    virtual CodeSequenceMacro& getTransducerGeometry();
+
+    /** Get Transducer Beam Steering
+     *  @return Reference to Transducer Beam Steering
+     */
+    virtual OFVector<CodeSequenceMacro*>& getTransducerBeamSteering();
+
+    /** Get Transducer Application
+     *  @return Reference to Transducer Application
+     */
+    virtual CodeSequenceMacro& getTransducerApplication();
+
+    /** Get Processing Function
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all values
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getProcessingFunction(OFString& value, const signed long pos = 0);
+    /** Get Mechanical Index
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getMechanicalIndex(Float64& value, const unsigned long pos = 0);
+
+    /** Get Bone Thermal Index
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getBoneThermalIndex(Float64& value, const unsigned long pos = 0);
+
+    /** Get Cranial Thermal Index
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all values
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getCranialThermalIndex(Float64& value, const unsigned long pos = 0);
+
+    /** Get Soft Tissue Thermal Index
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all values
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSoftTissueThermalIndex(Float64& value, const unsigned long pos = 0);
+
+    /** Get Depth(s) of Focus
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getDepthsOfFocus(Float64& value, const unsigned long pos = 0);
+
+    /** Get Depth(s) of Scan Field
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getDepthsOfScanField(Sint32& value, const unsigned long pos = 0);
+
+    /** Set Image Type. Image Type contains up to four values. Value 3 and 4 are
+     *  optional and can be left empty if desired. The values in their order
+     *  of occurrence are:
+     *  1) Pixel Data Characteristics: Either ORIGINAL or DERIVED
+     *  2) Patient Examination Characteristics: Fixed to "PRIMARY", thus cannot be
+     *  influenced through this function.
+     *  3) Image Flavor: Defined Terms listed in the standard
+     *  4) Derived Pixel Contrast: Defined Terms listed in the standard
+     *  @param  pixelDataChar Value 1 of Image Type
+     *  @param  imageFlavor Value 3 of Image Type
+     *  @param  derivedPixelContrast Value 4 of Image Type
+     *  @param  checkValue If OFTrue, the value is checked for conformance.
+     *  @return EC_Normal if setting was successful, error otherwise.
+     */
+    virtual OFCondition setImageType(const DcmIODTypes::IOD_ENHUSIMAGETYPE pixelDataChar,
+                                     const OFString& imageFlavor          = "",
+                                     const OFString& derivedPixelContrast = "",
+                                     const OFBool checkValue              = OFTrue);
+
+    /** Set Rows
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setRows(const Uint16 value, const OFBool checkValue = OFTrue);
+
+    /** Set Columns
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setColumns(const Uint16 value, const OFBool checkValue = OFTrue);
+    /** Set Bits Allocated
+     *  @param  value Value to be set, permitted values: 8 or 16
+     *  @param  checkValue Check 'value' for conformance if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setBitsAllocated(const Uint16 value, const OFBool checkValue = OFTrue);
+
+    /** Set Bits Stored
+     *  @param  value Value to be set, permitted values: 8 or 16
+     *  @param  checkValue Check 'value' for conformance if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setBitsStored(const Uint16 value, const OFBool checkValue = OFTrue);
+
+    /** Set High Bit
+     *  @param  value Value to be set, permitted values: 7 or 15
+     *  @param  checkValue Check 'value' for conformance if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setHighBit(const Uint16 value, const OFBool checkValue = OFTrue);
+
+    /** Set Dimension Organization Type
+     *  @param  value Value to be set, permitted values: "3D" or "3D_TEMPORAL"
+     *  @param  checkValue Check 'value' for conformance if enabled, including VR (CS) and VM (1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setDimensionOrganizationType(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Acquisition DateTime
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance if enabled, including VR (DT) and VM (1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setAcquisitionDateTime(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Acquisition Duration
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance if enabled,
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setAcquisitionDuration(const Float64 value, const OFBool checkValue = OFTrue);
+
+    /** Set Pixel Spacing
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance if enabled, including VR (DS) and VM (2)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPixelSpacing(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Position Measuring Device
+     *  @param  value Value to be set, permitted values: "RIGID" or "FREEHAND"
+     *  @param  checkValue Check 'value' for conformance if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPositionMeasuringDevice(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Lossy Image Compression
+     *  @param  value Value to be set, permitted values: "00" (not lossy compressed) or "01" (lossy compressed)
+     *  @param  checkValue Check 'value' for conformance if enabled, including VR (CS) and VM (1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setLossyImageCompression(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Lossy Image Compression Ratio
+     *  @param  value Value to be set, including VR (DS) and VM (1-n)
+     *  @param  checkValue Check 'value' for conformance if enabled, including VR (DS)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setLossyImageCompressionRatio(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Lossy Image Compression Method
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance if enabled, including VR (CS)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setLossyImageCompressionMethod(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Recognizable Visual Features
+     *  @param  value Value to be set, permitted values: "YES" or "NO"
+     *  @param  checkValue Check 'value' for conformance if enabled, including VR (CS) and VM (1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setRecognizableVisibleFeatures(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Processing Funcion
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance if enabled, including VR (LO) and VM (1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setProcessingFunction(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Mechanical Index
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance if enabled, including VR (DS) and VM (1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setMechanicalIndex(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Bone Thermal Index
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance if enabled, including VR (DS) and VM (1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setBoneThermalIndex(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Cranial Thermal Index
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance if enabled, including VR (DS) and VM (1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setCranialThermalIndex(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Soft Tissue Thermal Index
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance if enabled, including VR (DS) and VM (1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSoftTissueThermalIndex(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Depth(s) of Focus
+     *  @param  value Value to be set
+     *  @param  pos Index of the value to set (0..vm-1)
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency with
+     *          other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition
+    setDepthsOfFocus(const Float64 value, const unsigned long pos, const OFBool checkValue = OFTrue);
+
+    /** Set Depth(s) of Focus (convenience function)
+     *  @param  values Value(s) to be set
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency with
+     *          other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setDepthsOfFocus(const OFVector<Float64>& values, const OFBool checkValue = OFTrue);
+
+    /** Set Depth(s) of Scan Field
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance if enabled, including VR (IS) and VM (1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setDepthsOfScanField(const OFString& value, const OFBool checkValue = OFTrue);
 
 private:
+    /// This module's name ("EnhancedUSImageModule")
+    static const OFString m_ModuleName;
 
-  /// This module's name ("EnhancedUSImageModule")
-  static const OFString m_ModuleName;
-
-  /// Mandatory View and Slice Progression Direction
-  MandatoryViewAndSliceProgressionDirectionMacro m_MandatoryViewAndSliceProgressionDirection;
+    /// Mandatory View and Slice Progression Direction
+    MandatoryViewAndSliceProgressionDirectionMacro m_MandatoryViewAndSliceProgressionDirection;
 
-  /// General Anatomy Mandatory Macro
-  GeneralAnatomyMacro m_Anatomy;
+    /// General Anatomy Mandatory Macro
+    GeneralAnatomyMacro m_Anatomy;
 
-  /// Item of Transducer Scan Pattern Code Sequence
-  CodeSequenceMacro m_TransducerScanPattern;
+    /// Item of Transducer Scan Pattern Code Sequence
+    CodeSequenceMacro m_TransducerScanPattern;
 
-  /// Item of Transducer Geometry Code Sequence
-  CodeSequenceMacro m_TransducerGeometry;
+    /// Item of Transducer Geometry Code Sequence
+    CodeSequenceMacro m_TransducerGeometry;
 
-  /// Item of Transducer Beam Steering Code Sequence
-  OFVector<CodeSequenceMacro*> m_TransducerBeamSteering;
+    /// Item of Transducer Beam Steering Code Sequence
+    OFVector<CodeSequenceMacro*> m_TransducerBeamSteering;
 
-  /// Item of Transducer Application Code Sequence
-  CodeSequenceMacro m_TransducerApplication;
+    /// Item of Transducer Application Code Sequence
+    CodeSequenceMacro m_TransducerApplication;
 };
 
 #endif // MODENHUSIMAGE_H
index cfeaccb70d496a9a3b8ff02b15a6b05f6d0be8e2..22e81290f5a2fa47e20b7cf8263b2f3573ae1e48 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define MODENHUSSERIES_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofmem.h"
-#include "dcmtk/ofstd/ofvector.h"
-#include "dcmtk/ofstd/ofoption.h"
-#include "dcmtk/dcmiod/iodrules.h"
 #include "dcmtk/dcmiod/iodmacro.h"
+#include "dcmtk/dcmiod/iodrules.h"
 #include "dcmtk/dcmiod/modbase.h"
+#include "dcmtk/ofstd/ofmem.h"
+#include "dcmtk/ofstd/ofoption.h"
+#include "dcmtk/ofstd/ofvector.h"
 
 /** Class representing the Enhanced Ultrasound Series Module:
  *
- * Notation: "Attribute name: (VR, VM, Requirement Type)"
- * Modality: (CS, 1, 1)
- * Referenced Performed Procedure Step Sequence: (SQ, 1, 1C)
- * > SOP Instance Reference Macro
- * Performed Protocol Code Sequence: (SQ, 1, 1C)
- * > Code Sequence Macro
- * Not yet explicitly supported:
- * ----------------------------------------------
- * > Protocol Context Sequence: (SQ, 1-n, 3)
- * >> Content Item Macro
- * >> Content Item Modifier Sequence: (SQ, 1-n, 3)
- * >>> Content Item Macro
- * ----------------------------------------------
+ * Notation: "Attribute name: (VR, VM, Requirement Type)"\n
+ * Modality: (CS, 1, 1)\n
+ * Referenced Performed Procedure Step Sequence: (SQ, 1, 1C)\n
+ * &gt; SOP Instance Reference Macro\n
+ * Performed Protocol Code Sequence: (SQ, 1, 1C)\n
+ * &gt; Code Sequence Macro\n\n
+ *
+ * Not yet explicitly supported:\n
+ * ----------------------------------------------\n
+ * &gt; Protocol Context Sequence: (SQ, 1-n, 3)\n
+ * &gt;&gt; Content Item Macro\n
+ * &gt;&gt; Content Item Modifier Sequence: (SQ, 1-n, 3)\n
+ * &gt;&gt;&gt; Content Item Macro\n
+ * ----------------------------------------------\n
  * Performed Protocol Type: (CS, 1, 1C)
  */
 class DCMTK_DCMIOD_EXPORT IODEnhancedUSSeriesModule : public IODModule
 {
 
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  IODEnhancedUSSeriesModule(OFshared_ptr<DcmItem> item,
-                            OFshared_ptr<IODRules> rules);
-
-  /** Constructor
-   */
-  IODEnhancedUSSeriesModule();
-
-  /** Destructor
-   */
-  virtual ~IODEnhancedUSSeriesModule();
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of module ("EnhancedUSSeriesModule")
-   *  @return Name of the module ("EnhancedUSSeriesModule")
-   */
-  virtual OFString getName() const;
-
-  /** Read data into this module from given item
-   *  @param  source The item to read from
-   *  @param  clearOldData If OFTrue, old data in this module is cleared first (default: OFTrue)
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write this module to given item
-   *  @param  destination The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& destination);
-
-   /** Get Modality, always returns "US"
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getModality(OFString &value,
-                                  const signed long pos = 0) const;
-
-
-  /** Get Referenced Performed Procedure Step
-   *  @return Reference to the Referenced Performed Procedure Step information
-   */
-  virtual SOPInstanceReferenceMacro& getReferencedPPS();
-
-  /** Get Performed Protocol Code
-   *  @return Reference to the Performed Protocol information
-   */
-  virtual CodeSequenceMacro& getPerformedProtocolCode();
-
-  /** Get Performed Protocol Type
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getPerformedProtocolType(OFString &value,
-                                               const signed long pos = 0) const;
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     */
+    IODEnhancedUSSeriesModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
+
+    /** Constructor
+     */
+    IODEnhancedUSSeriesModule();
+
+    /** Destructor
+     */
+    virtual ~IODEnhancedUSSeriesModule();
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of module ("EnhancedUSSeriesModule")
+     *  @return Name of the module ("EnhancedUSSeriesModule")
+     */
+    virtual OFString getName() const;
+
+    /** Read data into this module from given item
+     *  @param  source The item to read from
+     *  @param  clearOldData If OFTrue, old data in this module is cleared first (default: OFTrue)
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write this module to given item
+     *  @param  destination The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& destination);
+
+    /** Get Modality, always returns "US"
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getModality(OFString& value, const signed long pos = 0) const;
+
+    /** Get Referenced Performed Procedure Step
+     *  @return Reference to the Referenced Performed Procedure Step information
+     */
+    virtual SOPInstanceReferenceMacro& getReferencedPPS();
+
+    /** Get Performed Protocol Code
+     *  @return Reference to the Performed Protocol information
+     */
+    virtual CodeSequenceMacro& getPerformedProtocolCode();
+
+    /** Get Performed Protocol Type
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPerformedProtocolType(OFString& value, const signed long pos = 0) const;
 
 private:
+    /// The name of this module ("EnhancedUSSeriesModule")
+    static const OFString m_ModuleName;
 
-  /// The name of this module ("EnhancedUSSeriesModule")
-  static const OFString m_ModuleName;
-
-  /// Referenced Performed Procedure Step Sequence
-  SOPInstanceReferenceMacro m_ReferencedPerformedProcedureStep;
+    /// Referenced Performed Procedure Step Sequence
+    SOPInstanceReferenceMacro m_ReferencedPerformedProcedureStep;
 
-  /// Performed Protocol Code Sequence (so far, without optional data)
-  CodeSequenceMacro m_PerformedProtocolCode;
+    /// Performed Protocol Code Sequence (so far, without optional data)
+    CodeSequenceMacro m_PerformedProtocolCode;
 };
 
 #endif // MODENHUSSERIES_H
index 77e72d7e30d8247ee9e6da34c8888abc369d5cf6..c5edb1891e9e19920ec20ccd703daa48de900935 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -42,47 +42,50 @@ class DCMTK_DCMIOD_EXPORT IODGeneralEquipmentModule : public IODModule
 {
 
 public:
-
     /** Convenient struct containing commonly used equipment information
      *  (for use by external code)
      */
     struct DCMTK_DCMIOD_EXPORT EquipmentInfo
     {
 
-      /** Default Constructor
-       */
-      EquipmentInfo() :
-        m_Manufacturer(),
-        m_ManufacturerModelName(),
-        m_DeviceSerialNumber(),
-        m_SoftwareVersions() {}
-
-      /** Convenience Constructor setting commonly used values
-       *  @param manufacturer Manufacturer
-       *  @param manufacturerModelName Manufacturer's model name
-       *  @param deviceSerialNumber Serial number
-       *  @param softwareVersions Software versions
-       */
-      EquipmentInfo(const OFString& manufacturer,
-                    const OFString& manufacturerModelName,
-                    const OFString& deviceSerialNumber,
-                    const OFString& softwareVersions) :
-        m_Manufacturer(manufacturer),
-        m_ManufacturerModelName(manufacturerModelName),
-        m_DeviceSerialNumber(deviceSerialNumber),
-        m_SoftwareVersions(softwareVersions) {}
-
-      /// Manufacturer (VM 1)
-      OFString m_Manufacturer;
-
-      /// Manufacturer's Model Name (VM 1)
-      OFString m_ManufacturerModelName;
-
-      /// Device Serial Number (VM 1)
-      OFString m_DeviceSerialNumber;
-
-      /// Software Version(s) (VM 1-n)
-      OFString m_SoftwareVersions;
+        /** Default Constructor
+         */
+        EquipmentInfo()
+            : m_Manufacturer()
+            , m_ManufacturerModelName()
+            , m_DeviceSerialNumber()
+            , m_SoftwareVersions()
+        {
+        }
+
+        /** Convenience Constructor setting commonly used values
+         *  @param manufacturer Manufacturer
+         *  @param manufacturerModelName Manufacturer's model name
+         *  @param deviceSerialNumber Serial number
+         *  @param softwareVersions Software versions
+         */
+        EquipmentInfo(const OFString& manufacturer,
+                      const OFString& manufacturerModelName,
+                      const OFString& deviceSerialNumber,
+                      const OFString& softwareVersions)
+            : m_Manufacturer(manufacturer)
+            , m_ManufacturerModelName(manufacturerModelName)
+            , m_DeviceSerialNumber(deviceSerialNumber)
+            , m_SoftwareVersions(softwareVersions)
+        {
+        }
+
+        /// Manufacturer (VM 1)
+        OFString m_Manufacturer;
+
+        /// Manufacturer's Model Name (VM 1)
+        OFString m_ManufacturerModelName;
+
+        /// Device Serial Number (VM 1)
+        OFString m_DeviceSerialNumber;
+
+        /// Software Version(s) (VM 1-n)
+        OFString m_SoftwareVersions;
     };
 
     /** Constructor
@@ -91,8 +94,7 @@ public:
      *  @param  rules The rule set for this class. If NULL, the class creates
      *          one from scratch and adds its values.
      */
-    IODGeneralEquipmentModule(OFshared_ptr<DcmItem> item,
-                              OFshared_ptr<IODRules> rules);
+    IODGeneralEquipmentModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
 
     /** Constructor
      */
@@ -103,7 +105,7 @@ public:
     virtual ~IODGeneralEquipmentModule();
 
     /** Resets rules to their original values
-    */
+     */
     virtual void resetRules();
 
     /** Get name of module
@@ -116,63 +118,55 @@ public:
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getManufacturer(OFString &value,
-                                        const signed long pos = 0) const;
+    virtual OFCondition getManufacturer(OFString& value, const signed long pos = 0) const;
 
     /** Get Institution Name
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getInstitutionName(OFString &value,
-                                           const signed long pos = 0) const;
+    virtual OFCondition getInstitutionName(OFString& value, const signed long pos = 0) const;
 
     /** Get Institution Address
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getInstitutionAddress(OFString &value,
-                                              const signed long pos = 0) const;
+    virtual OFCondition getInstitutionAddress(OFString& value, const signed long pos = 0) const;
 
     /** Get Station Name
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getStationName(OFString &value,
-                                       const signed long pos = 0) const;
+    virtual OFCondition getStationName(OFString& value, const signed long pos = 0) const;
 
     /** Get Institutional Department Name
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getInstitutionalDepartmentName(OFString &value,
-                                                       const signed long pos = 0) const;
+    virtual OFCondition getInstitutionalDepartmentName(OFString& value, const signed long pos = 0) const;
     /** Get Manufacturer's Model Name
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getManufacturerModelName(OFString &value,
-                                                 const signed long pos = 0) const;
+    virtual OFCondition getManufacturerModelName(OFString& value, const signed long pos = 0) const;
 
     /** Get Device Serial Number
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getDeviceSerialNumber(OFString &value,
-                                              const signed long pos = 0) const;
+    virtual OFCondition getDeviceSerialNumber(OFString& value, const signed long pos = 0) const;
 
     /** Get Software Version(s)
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getSoftwareVersions(OFString &value,
-                                            const signed long pos = 0) const;
+    virtual OFCondition getSoftwareVersions(OFString& value, const signed long pos = 0) const;
 
     /** Set Manufacturer
      *  @param  value Value to be set (single value only) or "" for no value
@@ -180,8 +174,7 @@ public:
      *          if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setManufacturer(const OFString &value,
-                                        const OFBool checkValue = OFTrue);
+    virtual OFCondition setManufacturer(const OFString& value, const OFBool checkValue = OFTrue);
 
     /** Set Institution Name
      *  @param  value Value to be set (single value only) or "" for no value
@@ -189,8 +182,7 @@ public:
      *          if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setInstitutionName(const OFString &value,
-                                           const OFBool checkValue = OFTrue);
+    virtual OFCondition setInstitutionName(const OFString& value, const OFBool checkValue = OFTrue);
 
     /** Set Institution Address
      *  @param  value Value to be set (single value only) or "" for no value
@@ -198,8 +190,7 @@ public:
      *          with other setter functions).
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setInstitutionAddress(const OFString &value,
-                                              const OFBool checkValue = OFTrue);
+    virtual OFCondition setInstitutionAddress(const OFString& value, const OFBool checkValue = OFTrue);
 
     /** Set Station Name
      *  @param  value Value to be set (single value only) or "" for no value
@@ -207,8 +198,7 @@ public:
      *          if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setStationName(const OFString &value,
-                                       const OFBool checkValue = OFTrue);
+    virtual OFCondition setStationName(const OFString& value, const OFBool checkValue = OFTrue);
 
     /** Set Institutional Department Name
      *  @param  value Value to be set (single value only) or "" for no value
@@ -216,8 +206,7 @@ public:
      *          if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setInstutionalDepartmentName(const OFString &value,
-                                                     const OFBool checkValue = OFTrue);
+    virtual OFCondition setInstutionalDepartmentName(const OFString& value, const OFBool checkValue = OFTrue);
 
     /** Set Manufacturer's Model Name
      *  @param  value Value to be set (single value only) or "" for no value
@@ -225,8 +214,7 @@ public:
      *          if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setManufacturerModelName(const OFString &value,
-                                                 const OFBool checkValue = OFTrue);
+    virtual OFCondition setManufacturerModelName(const OFString& value, const OFBool checkValue = OFTrue);
 
     /** Set Device Serial Number
      *  @param  value Value to be set (single value only) or "" for no value
@@ -234,8 +222,7 @@ public:
      *          if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setDeviceSerialNumber(const OFString &value,
-                                              const OFBool checkValue = OFTrue);
+    virtual OFCondition setDeviceSerialNumber(const OFString& value, const OFBool checkValue = OFTrue);
 
     /** Set Software Version(s)
      *  @param  value Value to be set (possibly multi-valued) or "" for no value
@@ -243,14 +230,11 @@ public:
      *          if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setSoftwareVersions(const OFString &value,
-                                            const OFBool checkValue = OFTrue);
+    virtual OFCondition setSoftwareVersions(const OFString& value, const OFBool checkValue = OFTrue);
 
 private:
-
     /// Name of the module ("GeneralEquipmentModule")
     OFString m_ModuleName;
 };
 
-
 #endif // MODEQUIPMENT_H
index 050722874418318baadadbfdbefba519cde5bc46..a49c339585e908189249b9d6ac1113c0c998a697 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -23,8 +23,8 @@
 #define MODFLOATINGPOINTIMAGEPIXEL_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmiod/modimagepixelbase.h"
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmiod/modimagepixelbase.h"
 
 /** Class representing Floating Point Image Pixel Module:
  *
@@ -41,100 +41,90 @@ class DCMTK_DCMIOD_EXPORT IODFloatingPointImagePixelModule : public IODImagePixe
 {
 
 public:
-
-  /// Data type of pixels
-  typedef Float32 value_type;
-
-  static const DcmTagKey pixel_data_tag;
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  IODFloatingPointImagePixelModule(OFshared_ptr<DcmItem> item,
-                                   OFshared_ptr<IODRules> rules);
-
-  /** Constructor
-   */
-  IODFloatingPointImagePixelModule();
-
-  /** Destructor
-   */
-  virtual ~IODFloatingPointImagePixelModule();
-
-  /** Read attributes from given item into this class
-   *  @param source  The source to read from
-   *  @param clearOldData If OFTrue, old data is cleared before reading. Otherwise
-   *         old data is overwritten (or amended)
-   *  @result EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write attributes from this class into given item
-   *  @param  destination The item to write to
-   *  @result EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& destination);
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of module
-   *  @return Name of the module ("FloatingPointImagePixelModule")
-   */
-  virtual OFString getName() const;
-
-  /** Get pixel data type, always returns DataType::FLOAT for this class.
-   *  @return The data type of the pixel data
-   */
-  virtual DataType getDataType() const;
-
-  /** Get Float Pixel Padding Value
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-  */
-  virtual OFCondition getFloatPixelPaddingValue(Float32& value,
-                                                const signed long pos = 0);
-
-  /** Get Float Pixel Padding Range Limit
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-  */
-  virtual OFCondition getFloatPixelPaddingRangeLimit(Float32& value,
-                                                     const signed long pos = 0);
-
-  /** Set Float Pixel Pixel Padding Value
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  checkValue Check 'value' for conformance with VR (FL) and consistency
-   *    with other attributes if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setFloatPixelPaddingValue(const Float32 value,
-                                                const OFBool checkValue = OFTrue);
-
-  /** Set Float Pixel Padding Range Limit
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  checkValue Check 'value' for conformance with VR (FL) and consistency
-   *    with other attributes if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setFloatPixelPaddingRangeLimit(const Float32 value,
-                                                     const OFBool checkValue = OFTrue);
+    /// Data type of pixels
+    typedef Float32 value_type;
+
+    static const DcmTagKey pixel_data_tag;
+
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     */
+    IODFloatingPointImagePixelModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
+
+    /** Constructor
+     */
+    IODFloatingPointImagePixelModule();
+
+    /** Destructor
+     */
+    virtual ~IODFloatingPointImagePixelModule();
+
+    /** Read attributes from given item into this class
+     *  @param source  The source to read from
+     *  @param clearOldData If OFTrue, old data is cleared before reading. Otherwise
+     *         old data is overwritten (or amended)
+     *  @result EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write attributes from this class into given item
+     *  @param  destination The item to write to
+     *  @result EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& destination);
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of module
+     *  @return Name of the module ("FloatingPointImagePixelModule")
+     */
+    virtual OFString getName() const;
+
+    /** Get pixel data type, always returns DataType::FLOAT for this class.
+     *  @return The data type of the pixel data
+     */
+    virtual DataType getDataType() const;
+
+    /** Get Float Pixel Padding Value
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getFloatPixelPaddingValue(Float32& value, const unsigned long pos = 0);
+
+    /** Get Float Pixel Padding Range Limit
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getFloatPixelPaddingRangeLimit(Float32& value, const unsigned long pos = 0);
+
+    /** Set Float Pixel Pixel Padding Value
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  checkValue Check 'value' for conformance with VR (FL) and consistency
+     *    with other attributes if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setFloatPixelPaddingValue(const Float32 value, const OFBool checkValue = OFTrue);
+
+    /** Set Float Pixel Padding Range Limit
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  checkValue Check 'value' for conformance with VR (FL) and consistency
+     *    with other attributes if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setFloatPixelPaddingRangeLimit(const Float32 value, const OFBool checkValue = OFTrue);
 
 private:
-
-  /// This module's name ("FloatingPointImagePixelModule")
-  static const OFString m_ModuleName;
-
+    /// This module's name ("FloatingPointImagePixelModule")
+    static const OFString m_ModuleName;
 };
 
-
 /** Class representing Double Floating Point Image Pixel Module:
  *
  *  Samples Per Pixel: (US, 1, 1)
@@ -146,101 +136,92 @@ private:
  *  Double Float Pixel Padding Value: (FD, 1, 3)
  *  Double Float Pixel Padding Range Limit: (FD, 1, 1C)
  */
-class DCMTK_DCMIOD_EXPORT IODDoubleFloatingPointImagePixelModule: public IODImagePixelBase
+class DCMTK_DCMIOD_EXPORT IODDoubleFloatingPointImagePixelModule : public IODImagePixelBase
 {
 
 public:
-
-  /// Data type of pixels
-  typedef Float64 value_type;
-
-  static const DcmTagKey pixel_data_tag;
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  IODDoubleFloatingPointImagePixelModule(OFshared_ptr<DcmItem> item,
-                                         OFshared_ptr<IODRules> rules);
-
-  /** Constructor
-   */
-  IODDoubleFloatingPointImagePixelModule();
-
-  /** Destructor
-   */
-  virtual ~IODDoubleFloatingPointImagePixelModule();
-
-  /** Read attributes from given item into this class
-   *  @param source  The source to read from
-   *  @param clearOldData If OFTrue, old data is cleared before reading. Otherwise
-   *         old data is overwritten (or amended)
-   *  @result EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write attributes from this class into given item
-   *  @param  destination The item to write to
-   *  @result EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& destination);
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of module
-   *  @return Name of the module ("DoubleFloatingPointImagePixelModule")
-   */
-  virtual OFString getName() const;
-
-  /** Get pixel data type, always returns DataType::DOUBLE for this class.
-   *  @return The data type of the pixel data
-   */
-  virtual DataType getDataType() const;
-
-  /** Get Double Float Pixel Padding Value
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-  */
-  virtual OFCondition getDoubleFloatPixelPaddingValue(Float64& value,
-                                                       const signed long pos = 0);
-
-  /** Get Double Float Pixel Padding Range Limit
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-  */
-  virtual OFCondition getDoubleFloatPixelPaddingRangeLimit(Float64& value,
-                                                            const signed long pos = 0);
-
-  /** Set Double Float Pixel Pixel Padding Value
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  checkValue Check 'value' for conformance with VR (FD) and consistency
-   *    with other attributes if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setDoubleFloatPixelPaddingValue(const Float64 value,
-                                                      const OFBool checkValue = OFTrue);
-
-  /** Set Double Float Pixel Padding Range Limit
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  checkValue Check 'value' for conformance with VR (FD) and consistency
-   *    with other attributes if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setDoubleFloatPixelPaddingRangeLimit(const Float64 value,
-                                                           const OFBool checkValue = OFTrue);
+    /// Data type of pixels
+    typedef Float64 value_type;
+
+    static const DcmTagKey pixel_data_tag;
+
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     */
+    IODDoubleFloatingPointImagePixelModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
+
+    /** Constructor
+     */
+    IODDoubleFloatingPointImagePixelModule();
+
+    /** Destructor
+     */
+    virtual ~IODDoubleFloatingPointImagePixelModule();
+
+    /** Read attributes from given item into this class
+     *  @param source  The source to read from
+     *  @param clearOldData If OFTrue, old data is cleared before reading. Otherwise
+     *         old data is overwritten (or amended)
+     *  @result EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write attributes from this class into given item
+     *  @param  destination The item to write to
+     *  @result EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& destination);
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of module
+     *  @return Name of the module ("DoubleFloatingPointImagePixelModule")
+     */
+    virtual OFString getName() const;
+
+    /** Get pixel data type, always returns DataType::DOUBLE for this class.
+     *  @return The data type of the pixel data
+     */
+    virtual DataType getDataType() const;
+
+    /** Get Double Float Pixel Padding Value
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getDoubleFloatPixelPaddingValue(Float64& value, const unsigned long pos = 0);
+
+    /** Get Double Float Pixel Padding Range Limit
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getDoubleFloatPixelPaddingRangeLimit(Float64& value, const unsigned long pos = 0);
+
+    /** Set Double Float Pixel Pixel Padding Value
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  checkValue Check 'value' for conformance with VR (FD) and consistency
+     *    with other attributes if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setDoubleFloatPixelPaddingValue(const Float64 value, const OFBool checkValue = OFTrue);
+
+    /** Set Double Float Pixel Padding Range Limit
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  checkValue Check 'value' for conformance with VR (FD) and consistency
+     *    with other attributes if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setDoubleFloatPixelPaddingRangeLimit(const Float64 value, const OFBool checkValue = OFTrue);
 
 private:
-
-  /// This module's name ("DoubleFloatingPointImagePixelModule")
-  static const OFString m_ModuleName;
-
+    /// This module's name ("DoubleFloatingPointImagePixelModule")
+    static const OFString m_ModuleName;
 };
 
 #endif // MODFLOATINGPOINTIMAGEPIXEL_H
index 76d7519fd5c9b2ad2bf579ba24828bb6d506d7dd..9f14a90d92dc16d46334d5b8be3a8fb3ea03672b 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -35,81 +35,72 @@ class DCMTK_DCMIOD_EXPORT IODFoRModule : public IODModule
 {
 
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  IODFoRModule(OFshared_ptr<DcmItem> item,
-               OFshared_ptr<IODRules> rules);
-  /** Constructor
-   */
-  IODFoRModule();
-
-  /** Destructor
-   */
-  virtual ~IODFoRModule();
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of module
-   *  @return Name of the module ("FrameOfReferenceModule")
-   */
-  virtual OFString getName() const;
-
-  /** Get Frame of Reference UID
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getFrameOfReferenceUID(OFString &value,
-                                             const signed long pos = 0) const;
-
-  /** Get Position Reference Indicator
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getPositionReferenceIndicator(OFString &value,
-                                                    const signed long pos = 0) const;
-
-  /** Set Frame of Reference UID
-   *  @param  value Value to be set (single value only).  If an empty string is passed,
-   *          the value "1" is set when displaying or writing the document since
-   *          the corresponding DICOM attribute is mandatory.
-   *  @param  checkValue Check 'value' for conformance with VR (UI) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setFrameOfReferenceUID(const OFString &value,
-                                             const OFBool checkValue = OFTrue);
-
-  /** Set Position Reference Indicator
-   *  @param  value Value to be set (single value only).  If an empty string is passed,
-   *          the value "1" is set when displaying or writing the document since
-   *          the corresponding DICOM attribute is mandatory.
-   *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPositionReferenceIndicator(const OFString &value,
-                                                    const OFBool checkValue = OFTrue);
-
-  /** Make sure that the module contains a Frame of Reference Instance UID, i.e.\
-   *  a new one is created if empty. An invalid UID is corrected if desired.
-   *  @param  correctInvalid Correct invalid UID if OFTrue, otherwise do nothing
-   *
-   */
-  void ensureFrameOfReferenceUID(const OFBool correctInvalid = OFFalse);
-
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     */
+    IODFoRModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
+    /** Constructor
+     */
+    IODFoRModule();
+
+    /** Destructor
+     */
+    virtual ~IODFoRModule();
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of module
+     *  @return Name of the module ("FrameOfReferenceModule")
+     */
+    virtual OFString getName() const;
+
+    /** Get Frame of Reference UID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getFrameOfReferenceUID(OFString& value, const signed long pos = 0) const;
+
+    /** Get Position Reference Indicator
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPositionReferenceIndicator(OFString& value, const signed long pos = 0) const;
+
+    /** Set Frame of Reference UID
+     *  @param  value Value to be set (single value only).  If an empty string is passed,
+     *          the value "1" is set when displaying or writing the document since
+     *          the corresponding DICOM attribute is mandatory.
+     *  @param  checkValue Check 'value' for conformance with VR (UI) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setFrameOfReferenceUID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Position Reference Indicator
+     *  @param  value Value to be set (single value only).  If an empty string is passed,
+     *          the value "1" is set when displaying or writing the document since
+     *          the corresponding DICOM attribute is mandatory.
+     *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPositionReferenceIndicator(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Make sure that the module contains a Frame of Reference Instance UID, i.e.\
+     *  a new one is created if empty. An invalid UID is corrected if desired.
+     *  @param  correctInvalid Correct invalid UID if OFTrue, otherwise do nothing
+     *
+     */
+    void ensureFrameOfReferenceUID(const OFBool correctInvalid = OFFalse);
 
 private:
-
-  /// Module name "FrameOfReferenceModule"
-  static const OFString m_ModuleName;
-
+    /// Module name "FrameOfReferenceModule"
+    static const OFString m_ModuleName;
 };
 
 #endif // MODFOR_H
index 7cb3402f6710a41237f97bd0dfa42dd57b113029..8d4a09a4173838e5015021ed00c62f34951c9541 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #include "dcmtk/dcmiod/iodrules.h"
 #include "dcmtk/dcmiod/modbase.h"
 
-
 /** Class representing the General Image Module:
 *
 * Instance Number: (IS, 1, 2)
 * Patient Orientation: (CS, 2, 2)
 * Content Date:    (DA, 1, 2C)
 * Content Time:    (TM, 1, 2C)
 * Image Type:      (CS, 1, 2-n)
 * Acquisition Number (IS, 1, 3)
 * Acquisition Date (DA, 1, 3)
 * Acquisition Time (TM, 1, 3)
 * Acquisition Date Time (DT, 1, 3)
 * Image Comments   (LT, 1, 3)
 * Burned In Annotation (CS, 1, 3)
 * Recognizable Visual Features (CS, 1, 3)
 * Lossy Image Compression (CS, 1, 3)
 * Lossy Image Compression Ratio (DS, 1, 3)
 * Lossy Image Compression Method (CS, 1-n, 3)
 * Presentation LUT Shape (CS, 1, 3)
 * Irradiation Event UID (CS, 1-n, 3)
 *
 */
+ *
+ * Instance Number: (IS, 1, 2)
+ * Patient Orientation: (CS, 2, 2)
+ * Content Date:    (DA, 1, 2C)
+ * Content Time:    (TM, 1, 2C)
+ * Image Type:      (CS, 1, 2-n)
+ * Acquisition Number (IS, 1, 3)
+ * Acquisition Date (DA, 1, 3)
+ * Acquisition Time (TM, 1, 3)
+ * Acquisition Date Time (DT, 1, 3)
+ * Image Comments   (LT, 1, 3)
+ * Burned In Annotation (CS, 1, 3)
+ * Recognizable Visual Features (CS, 1, 3)
+ * Lossy Image Compression (CS, 1, 3)
+ * Lossy Image Compression Ratio (DS, 1, 3)
+ * Lossy Image Compression Method (CS, 1-n, 3)
+ * Presentation LUT Shape (CS, 1, 3)
+ * Irradiation Event UID (CS, 1-n, 3)
+ *
+ */
 class DCMTK_DCMIOD_EXPORT IODGeneralImageModule : public IODModule
 {
 
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  IODGeneralImageModule(OFshared_ptr<DcmItem> item,
-                        OFshared_ptr<IODRules> rules);
-
-  /** Constructor
-   */
-  IODGeneralImageModule();
-
-  /** Destructor
-   */
-  virtual ~IODGeneralImageModule();
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of module
-   *  @return Name of the module ("GeneralImageModule")
-   */
-  virtual OFString getName() const;
-
-  /** Get Instance Number
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getInstanceNumber(OFString &value,
-                                        const signed long pos = 0);
-
-  /** Get Patient Orientation
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return  EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getPatientOrientation(OFString &value,
-                                            const signed long pos = 0);
-
-  /** Get Content Date
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getContentDate(OFString &value,
-                                     const signed long pos = 0);
-
-  /** Get Content Time
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getContentTime(OFString &value,
-                                     const signed long pos = 0);
-
-  /** Get Image Type
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getImageType(OFString &value,
-                                   const signed long pos = 0);
-
-  /** Get Acquisition Number
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getAcquisitionNumber(OFString &value,
-                                           const signed long pos = 0);
-
-  /** Get Acquisition Date
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getAcquisitionDate(OFString &value,
-                                         const signed long pos = 0);
-
-  /** Get Acquisition Time
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getAcquisitionTime(OFString &value,
-                                         const signed long pos = 0);
-
-  /** Get Acquisition Date Time
-   *  @param  value  Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getAcquisitionDateTime(OFString &value,
-                                             const signed long pos = 0);
-
-  /** Get Image Comments
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getImageComments(OFString &value,
-                                       const signed long pos = 0);
-
-  /** Get Burned In Annotation
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getBurnedInAnnotation(OFString &value,
-                                            const signed long pos = 0);
-
-  /** Get Recognizable Visual Features
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos  Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getRecognizableVisualFeatures(OFString &value,
-                                                    const signed long pos = 0);
-
-  /** Get Lossy Image Compression
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getLossyImageCompression(OFString &value,
-                                               const signed long pos = 0);
-
-  /** Get Lossy Image Compression
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getLossyImageCompressionRatio(OFString &value,
-                                                    const signed long pos = 0);
-
-  /** Get Lossy Image Compression Method
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getLossyImageCompressionMethod(OFString &value,
-                                                    const signed long pos = 0);
-
-  /** Get Presentation LUT Shape
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getPresentationLUTShape(OFString &value,
-                                              const signed long pos = 0);
-
-  /** Get Irridation Event UID
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos  Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getIrradiationEventUID(OFString &value,
-                                             const signed long pos = 0);
-
-  /** Set Instance Number
-   *  @param  value Value to be set (single value only).
-   *  @param  checkValue Check 'value' for conformance with VR (IS) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setInstanceNumber(const OFString &value,
-                                        const OFBool checkValue = OFTrue);
-
-  /** Set Patient Orientation
-   *  @param  value Value to be set (single value only).
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (2) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPatientOrientation(const OFString &value,
-                                            const OFBool checkValue = OFTrue);
-
-  /** Set Content Date
-   *  @param  value Value to be set (single value only).
-   *  @param  checkValue Check 'value' for conformance with VR (DA) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setContentDate(const OFString &value,
-                                     const OFBool checkValue = OFTrue);
-
-  /** Set Content Time
-   *  @param  value Value to be set (single value only).
-   *  @param  checkValue Check 'value' for conformance with VR (TM) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setContentTime(const OFString &value,
-                                     const OFBool checkValue = OFTrue);
-
-
-  /** Set Image Type
-   *  @param  value Value to be set (single value only).
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (2-n) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setImageType(const OFString &value,
-                                   const OFBool checkValue = OFTrue);
-
-  /** Set Acquisition Number
-   *  @param  value Value to be set (single value only).
-   *  @param  checkValue Check 'value' for conformance with VR (IS) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setAcquisitionNumber(const OFString &value,
-                                           const OFBool checkValue = OFTrue);
-
-  /** Set Acquisition Date
-   *  @param  value Value to be set (single value only).
-   *  @param  checkValue Check 'value' for conformance with VR (DA) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setAcquisitionDate(const OFString &value,
-                                         const OFBool checkValue = OFTrue);
-
-  /** Set Acquisition Time
-   *  @param  value Value to be set (single value only).
-   *  @param  checkValue Check 'value' for conformance with VR (TM) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setAcquisitionTime(const OFString &value,
-                                         const OFBool checkValue = OFTrue);
-
-  /** Set Acquisition Date Time
-   *  @param  value Value to be set (single value only).
-   *  @param  checkValue Check 'value' for conformance with VR (DT) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setAcquisitionDateTime(const OFString &value,
-                                             const OFBool checkValue = OFTrue);
-
-  /** Set Image Comments
-   *  @param  value Value to be set (single value only).
-   *  @param  checkValue Check 'value' for conformance with VR (LT) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setImageComments(const OFString &value,
-                                       const OFBool checkValue = OFTrue);
-
-  /** Set Burned In Annotation
-   *  @param  value Value to be set (single value only).
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setBurnedInAnnotation(const OFString &value,
-                                            const OFBool checkValue = OFTrue);
-
-  /** Set Recognizable Visual Features
-   *  @param  value Value to be set (single value only).
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRecognizableVisualFeatures(const OFString &value,
-                                                    const OFBool checkValue = OFTrue);
-
-  /** Set Lossy Image Compression
-   *  @param  value Value to be set (single value only).
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setLossyImageCompression(const OFString &value,
-                                               const OFBool checkValue = OFTrue);
-
-  /** Set Lossy Image Compression Ratio
-   *  @param  value Value to be set (single value only).
-   *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setLossyImageCompressionRatio(const OFString &value,
-                                                    const OFBool checkValue = OFTrue);
-
-  /** Set Lossy Image Compression method
-   *  @param  value Value to be set (single value only).
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1-n) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setLossyImageCompressionMethod(const OFString &value,
-                                                     const OFBool checkValue = OFTrue);
-
-  /** Set Presentation LUT Shape
-   *  @param  value Value to be set (single value only).
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPresentationLUTShape(const OFString &value,
-                                              const OFBool checkValue = OFTrue);
-
-  /** Set Irradiation Event UID
-   *  @param  value Value to be set (single value only).
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1-n) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setIrradiationEventUID(const OFString &value,
-                                             const OFBool checkValue = OFTrue);
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     */
+    IODGeneralImageModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
+
+    /** Constructor
+     */
+    IODGeneralImageModule();
+
+    /** Destructor
+     */
+    virtual ~IODGeneralImageModule();
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of module
+     *  @return Name of the module ("GeneralImageModule")
+     */
+    virtual OFString getName() const;
+
+    /** Get Instance Number
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getInstanceNumber(OFString& value, const signed long pos = 0);
+
+    /** Get Patient Orientation
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return  EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPatientOrientation(OFString& value, const signed long pos = 0);
+
+    /** Get Content Date
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getContentDate(OFString& value, const signed long pos = 0);
+
+    /** Get Content Time
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getContentTime(OFString& value, const signed long pos = 0);
+
+    /** Get Image Type
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getImageType(OFString& value, const signed long pos = 0);
+
+    /** Get Acquisition Number
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getAcquisitionNumber(OFString& value, const signed long pos = 0);
+
+    /** Get Acquisition Date
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getAcquisitionDate(OFString& value, const signed long pos = 0);
+
+    /** Get Acquisition Time
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getAcquisitionTime(OFString& value, const signed long pos = 0);
+
+    /** Get Acquisition Date Time
+     *  @param  value  Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getAcquisitionDateTime(OFString& value, const signed long pos = 0);
+
+    /** Get Image Comments
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getImageComments(OFString& value, const signed long pos = 0);
+
+    /** Get Burned In Annotation
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getBurnedInAnnotation(OFString& value, const signed long pos = 0);
+
+    /** Get Recognizable Visual Features
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos  Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getRecognizableVisualFeatures(OFString& value, const signed long pos = 0);
+
+    /** Get Lossy Image Compression
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getLossyImageCompression(OFString& value, const signed long pos = 0);
+
+    /** Get Lossy Image Compression
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getLossyImageCompressionRatio(OFString& value, const signed long pos = 0);
+
+    /** Get Lossy Image Compression Method
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getLossyImageCompressionMethod(OFString& value, const signed long pos = 0);
+
+    /** Get Presentation LUT Shape
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPresentationLUTShape(OFString& value, const signed long pos = 0);
+
+    /** Get Irridation Event UID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos  Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getIrradiationEventUID(OFString& value, const signed long pos = 0);
+
+    /** Set Instance Number
+     *  @param  value Value to be set (single value only).
+     *  @param  checkValue Check 'value' for conformance with VR (IS) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setInstanceNumber(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Patient Orientation
+     *  @param  value Value to be set (single value only).
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (2) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPatientOrientation(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Content Date
+     *  @param  value Value to be set (single value only).
+     *  @param  checkValue Check 'value' for conformance with VR (DA) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setContentDate(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Content Time
+     *  @param  value Value to be set (single value only).
+     *  @param  checkValue Check 'value' for conformance with VR (TM) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setContentTime(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Image Type
+     *  @param  value Value to be set (single value only).
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (2-n) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setImageType(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Acquisition Number
+     *  @param  value Value to be set (single value only).
+     *  @param  checkValue Check 'value' for conformance with VR (IS) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setAcquisitionNumber(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Acquisition Date
+     *  @param  value Value to be set (single value only).
+     *  @param  checkValue Check 'value' for conformance with VR (DA) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setAcquisitionDate(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Acquisition Time
+     *  @param  value Value to be set (single value only).
+     *  @param  checkValue Check 'value' for conformance with VR (TM) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setAcquisitionTime(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Acquisition Date Time
+     *  @param  value Value to be set (single value only).
+     *  @param  checkValue Check 'value' for conformance with VR (DT) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setAcquisitionDateTime(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Image Comments
+     *  @param  value Value to be set (single value only).
+     *  @param  checkValue Check 'value' for conformance with VR (LT) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setImageComments(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Burned In Annotation
+     *  @param  value Value to be set (single value only).
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setBurnedInAnnotation(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Recognizable Visual Features
+     *  @param  value Value to be set (single value only).
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setRecognizableVisualFeatures(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Lossy Image Compression
+     *  @param  value Value to be set (single value only).
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setLossyImageCompression(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Lossy Image Compression Ratio
+     *  @param  value Value to be set (single value only).
+     *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setLossyImageCompressionRatio(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Lossy Image Compression method
+     *  @param  value Value to be set (single value only).
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1-n) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setLossyImageCompressionMethod(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Helper method to set lossy compression flag of the to "01" as well as ratios
+     *  and methods in one go.
+     *  @param  ratios Compression ratios (separated by backslash) of the applied
+     *          lossy compression steps. Only one value (and no backslash) if only
+     *          one step was performed.
+     *  @param  methods Methods (separated by backslash) of the applied
+     *          lossy compression steps. Only one value (and no backslash) if only
+     *          one step was performed.
+     *  @param  checkValues If OFTrue, the data provided is checked for validity
+     *  @return EC_Normal if lossy compression info could be set, error code otherwise
+     */
+    virtual OFCondition
+    setLossyImageCompressionFlag(const OFString& ratios, const OFString& methods, const OFBool checkValues = OFTrue);
+
+    /** Set Presentation LUT Shape
+     *  @param  value Value to be set (single value only).
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPresentationLUTShape(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Irradiation Event UID
+     *  @param  value Value to be set (single value only).
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1-n) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setIrradiationEventUID(const OFString& value, const OFBool checkValue = OFTrue);
 
 private:
-
-  /// The module's name ("GeneralIamgeModule")
-  static const OFString m_ModuleName;
+    /// The module's name ("GeneralIamgeModule")
+    static const OFString m_ModuleName;
 };
 
 #endif // MODGENERALIMAGE_H
index 38d1653504e5eae80683ef96f0356c86095a4e20..c6781b87dd0973cd0c10e847685f2abdf1ad85b1 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -23,9 +23,9 @@
 #define MODGENERALSERIES_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmiod/modbase.h"
 #include "dcmtk/dcmiod/ioddef.h"
 #include "dcmtk/dcmiod/iodmacro.h"
+#include "dcmtk/dcmiod/modbase.h"
 
 /** Class representing the General Series Module:
  *
@@ -46,278 +46,249 @@ class DCMTK_DCMIOD_EXPORT IODGeneralSeriesModule : public IODModule
 {
 
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  IODGeneralSeriesModule(OFshared_ptr<DcmItem> item,
-                         OFshared_ptr<IODRules> rules);
-
-  /** Constructor
-   */
-  IODGeneralSeriesModule();
-
-  /** Destructor
-   */
-  virtual ~IODGeneralSeriesModule();
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Set missing values by inventing "default values". Automatically
-   *  called during write() by IODComponent.
-   */
-  virtual void inventMissing();
-
-  /** Get name of module
-   *  @return Name of the module ("GeneralSeriesModule")
-   */
-  virtual OFString getName() const;
-
-  /** Make sure that the module contains a Series Instance UID, i.e.\ a new one
-   *  is created if empty. An invalid UID is corrected if desired.
-   *  @param  correctInvalid Correct invalid UID if OFTrue, otherwise do nothing
-   */
-  virtual void ensureInstanceUID(const OFBool correctInvalid = OFFalse);
-
-  /** Read attributes from given item into this class
-   *  @param source  The source to read from
-   *  @param clearOldData If OFTrue, old data is cleared before reading. Otherwise
-   *         old data is overwritten (or amended)
-   *  @result EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write attributes from this class into given item
-   *  @param  destination The item to write to
-   *  @result EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& destination);
-
-   /** Get Modality
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getModality(OFString &value,
-                                  const signed long pos = 0) const;
-
-  /** Get series instance UID
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getSeriesInstanceUID(OFString &value,
-                                            const signed long pos = 0) const;
-
-   /** Get Series Number
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getSeriesNumber(OFString &value,
-                                      const signed long pos = 0) const;
-
-   /** Get Laterality
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getLaterality(OFString &value,
-                                      const signed long pos = 0) const;
-
-   /** Get Series Date
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getSeriesDate(OFString &value,
-                                    const signed long pos = 0) const;
-
-   /** Get Series Time
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getSeriesTime(OFString &value,
-                                    const signed long pos = 0) const;
-
-   /** Get Performing Physician's Name
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getPerformingPhysicianName(OFString &value,
-                                                 const signed long pos = 0) const;
-
-   /** Get Protocol Name
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getProtocolName(OFString &value,
-                                      const signed long pos = 0) const;
-
-   /** Get Series Description
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos  Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getSeriesDescription(OFString &value,
-                                           const signed long pos = 0) const;
-
-   /** Get Operators' Name
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getOperatorsName(OFString &value,
-                                       const signed long pos = 0) const;
-
-   /** Get Body Part Examined
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getBodyPartExamined(OFString &value,
-                                          const signed long pos = 0) const;
-
-   /** Get Patient Position
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getPatientPosition(OFString &value,
-                                         const signed long pos = 0) const;
-
-  /** Get reference to Referenced Performed Procedure Step
-   *  @return Reference to PPS
-   */
-  virtual SOPInstanceReferenceMacro& getReferencedPPS();
-
-  /** Set Modality
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setModality(const OFString &value,
-                                  const OFBool checkValue = OFTrue);
-
-  /** Set Series Instance UID
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (UI) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSeriesInstanceUID(const OFString &value,
-                                           const OFBool checkValue = OFTrue);
-
-  /** Set Series Number
-   *  @param  value Value to be set (single value only).  If an empty string is,
-   *          passed, the value "1" is set when displaying or writing the document
-   *          since the corresponding DICOM attribute is mandatory.
-   *  @param  checkValue Check 'value' for conformance with VR (IS) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSeriesNumber(const OFString &value,
-                                      const OFBool checkValue = OFTrue);
-
-  /** Set Laterality
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setLaterality(const DcmIODTypes::IOD_LATERALITY value,
-                                    const OFBool checkValue = OFTrue);
-
-  /** Set Series Date
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (DA) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSeriesDate(const OFString &value,
-                                    const OFBool checkValue = OFTrue);
-
-  /** Set Series Time
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (TM) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSeriesTime(const OFString &value,
-                                    const OFBool checkValue = OFTrue);
-
-  /** Set Performing Physician Name
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (PN) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPerformingPhysicianName(const OFString &value,
-                                                 const OFBool checkValue = OFTrue);
-
-  /** Set Protocol Name
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setProtocolName(const OFString &value,
-                                      const OFBool checkValue = OFTrue);
-
-  /** Set Series Description
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSeriesDescription(const OFString &value,
-                                            const OFBool checkValue = OFTrue);
-
-  /** Set Operators' Name
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance with VR (PN) and VM (1-n)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setOperatorsName(const OFString &value,
-                                       const OFBool checkValue = OFTrue);
-
-  /** Set Body Part Examined
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setBodyPartExamined(const OFString &value,
-                                          const OFBool checkValue = OFTrue);
-
-  /** Set Patient Position
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPatientPosition(const OFString &value,
-                                        const OFBool checkValue = OFTrue);
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     */
+    IODGeneralSeriesModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
+
+    /** Constructor
+     */
+    IODGeneralSeriesModule();
+
+    /** Destructor
+     */
+    virtual ~IODGeneralSeriesModule();
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Set missing values by inventing "default values". Automatically
+     *  called during write() by IODComponent.
+     */
+    virtual void inventMissing();
+
+    /** Get name of module
+     *  @return Name of the module ("GeneralSeriesModule")
+     */
+    virtual OFString getName() const;
+
+    /** Make sure that the module contains a Series Instance UID, i.e.\ a new one
+     *  is created if empty. An invalid UID is corrected if desired.
+     *  @param  correctInvalid Correct invalid UID if OFTrue, otherwise do nothing
+     */
+    virtual void ensureInstanceUID(const OFBool correctInvalid = OFFalse);
+
+    /** Read attributes from given item into this class
+     *  @param source  The source to read from
+     *  @param clearOldData If OFTrue, old data is cleared before reading. Otherwise
+     *         old data is overwritten (or amended)
+     *  @result EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write attributes from this class into given item
+     *  @param  destination The item to write to
+     *  @result EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& destination);
+
+    /** Get Modality
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getModality(OFString& value, const signed long pos = 0) const;
+
+    /** Get series instance UID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSeriesInstanceUID(OFString& value, const signed long pos = 0) const;
+
+    /** Get Series Number
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSeriesNumber(OFString& value, const signed long pos = 0) const;
+
+    /** Get Laterality
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getLaterality(OFString& value, const signed long pos = 0) const;
+
+    /** Get Series Date
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSeriesDate(OFString& value, const signed long pos = 0) const;
+
+    /** Get Series Time
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSeriesTime(OFString& value, const signed long pos = 0) const;
+
+    /** Get Performing Physician's Name
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPerformingPhysicianName(OFString& value, const signed long pos = 0) const;
+
+    /** Get Protocol Name
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getProtocolName(OFString& value, const signed long pos = 0) const;
+
+    /** Get Series Description
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos  Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSeriesDescription(OFString& value, const signed long pos = 0) const;
+
+    /** Get Operators' Name
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getOperatorsName(OFString& value, const signed long pos = 0) const;
+
+    /** Get Body Part Examined
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getBodyPartExamined(OFString& value, const signed long pos = 0) const;
+
+    /** Get Patient Position
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPatientPosition(OFString& value, const signed long pos = 0) const;
+
+    /** Get reference to Referenced Performed Procedure Step
+     *  @return Reference to PPS
+     */
+    virtual SOPInstanceReferenceMacro& getReferencedPPS();
+
+    /** Set Modality
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setModality(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Series Instance UID
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (UI) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSeriesInstanceUID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Series Number
+     *  @param  value Value to be set (single value only).  If an empty string is,
+     *          passed, the value "1" is set when displaying or writing the document
+     *          since the corresponding DICOM attribute is mandatory.
+     *  @param  checkValue Check 'value' for conformance with VR (IS) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSeriesNumber(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Laterality
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setLaterality(const DcmIODTypes::IOD_LATERALITY value, const OFBool checkValue = OFTrue);
+
+    /** Set Series Date
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (DA) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSeriesDate(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Series Time
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (TM) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSeriesTime(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Performing Physician Name
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (PN) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPerformingPhysicianName(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Protocol Name
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setProtocolName(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Series Description
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSeriesDescription(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Operators' Name
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance with VR (PN) and VM (1-n)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setOperatorsName(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Body Part Examined
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setBodyPartExamined(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Patient Position
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPatientPosition(const OFString& value, const OFBool checkValue = OFTrue);
 
 private:
+    /// The name of this module ("GeneralSeriesModule")
+    static const OFString m_ModuleName;
 
-  /// The name of this module ("GeneralSeriesModule")
-  static const OFString m_ModuleName;
-
-  /// Referenced Performed Procedure Step Sequence
-  SOPInstanceReferenceMacro m_ReferencedPPS;
-
+    /// Referenced Performed Procedure Step Sequence
+    SOPInstanceReferenceMacro m_ReferencedPPS;
 };
 
 #endif // MODGENERALSERIES_H
index 70d289cdf3c4b0a47f7cdc649fb2c22726c9de72..c2afd4d7086dbd059b4ba1f43f2279fa7bece6fb 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define MODGENERALSTUDY_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmiod/modbase.h"
 #include "dcmtk/dcmiod/iodmacro.h"
+#include "dcmtk/dcmiod/modbase.h"
 
 /** Class representing the General Study Module:
 * Notation is "Attribute Name: (VR, VM, Type)"
 *
 * Study Instance UID: (UI, 1, 1)
 * Study Date: (DA, 1, 2)
 * Study Time: (TM, 1, 2)
 * Referring Physician's Name: (PN, 1, 2)
 * Study ID: (SH, 1, 2)
 * Accession Number: (SH, 1, 2)
 * Study Description: (LO, 1, 3)
 * Issuer of Accession Number Sequence: (SQ, 1, 3)
 * Procedure Code Sequence: (SQ, 1-n, 3)
 * Reason for Performed Procedure Code Sequence: (SQ, 1-n, 3)
 */
+ * Notation is "Attribute Name: (VR, VM, Type)"
+ *
+ * Study Instance UID: (UI, 1, 1)
+ * Study Date: (DA, 1, 2)
+ * Study Time: (TM, 1, 2)
+ * Referring Physician's Name: (PN, 1, 2)
+ * Study ID: (SH, 1, 2)
+ * Accession Number: (SH, 1, 2)
+ * Study Description: (LO, 1, 3)
+ * Issuer of Accession Number Sequence: (SQ, 1, 3)
+ * Procedure Code Sequence: (SQ, 1-n, 3)
+ * Reason for Performed Procedure Code Sequence: (SQ, 1-n, 3)
+ */
 class DCMTK_DCMIOD_EXPORT IODGeneralStudyModule : public IODModule
 {
 
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  IODGeneralStudyModule(OFshared_ptr<DcmItem> item,
-                        OFshared_ptr<IODRules> rules);
-  /** Constructor
-   */
-  IODGeneralStudyModule();
-
-  /** Destructor
-   */
-  virtual ~IODGeneralStudyModule();
-
-  /** Set missing values by inventing "default values". Automatically
-   *  called during write() by IODComponent.
-   */
-  virtual void inventMissing();
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of module
-   *  @return Name of the module ("GeneralStudyModule")
-   */
-  virtual OFString getName() const;
-
-  /** Clear (removes) all attributes handled by the modules of this component.
-   *  Rules are not reset.
-   */
-  virtual void clearData();
-
-  /** Read data into this module from given item
-   *  @param  source The item to read from
-   *  @param  clearOldData If OFTrue, old data in this module is cleared first (default: OFTrue)
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write this module to given item
-   *  @param  destination The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& destination);
-
-  /** Make sure that the module contains a Study Instance UID, i.e.\ a new one
-   *  is created if empty. An invalid UID is corrected if desired.
-   *  @param  correctInvalid Correct invalid UID if OFTrue, otherwise do nothing
-   */
-  virtual void ensureInstanceUID(const OFBool correctInvalid = OFFalse);
-
- /** Get Study Instance UID
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getStudyInstanceUID(OFString &value,
-                                          const signed long pos = 0) const;
-
-   /** Get Study Date
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos   Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getStudyDate(OFString &value,
-                                    const signed long pos = 0) const;
-
-   /** Get Study Time
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos  Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getStudyTime(OFString &value,
-                                    const signed long pos = 0) const;
-
-   /** Get Referring Physician's Name
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getReferringPhysicianName(OFString &value,
-                                                const signed long pos = 0) const;
-
-   /** Get Study ID
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getStudyID(OFString &value,
-                                 const signed long pos = 0) const;
-
-   /** Get Accession Number
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getAccessionNumber(OFString &value,
-                                         const signed long pos = 0) const;
-
-   /** Get Study Description
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getStudyDescription(OFString &value,
-                                          const signed long pos = 0) const;
-
-  /** Get reference to content of Issuer of Accession Number Sequence
-   *  @return Reference to single item of Issuer of Accession Number Sequence
-   */
-  virtual HL7HierarchicDesignatorMacro& getIssuerOfAccesionNumber();
-
-  /** Get reference to content of Procedure Code Sequence
-   *  @return Reference to items of Procedure Code Sequence
-   */
-  virtual OFVector<CodeSequenceMacro*>& getProcedureCodeSequence();
-
-  /** Get reference to content of Reason for Performed Procedure Code Sequence
-   *  @return Reference to items of Procedure Code Sequence
-   */
-  virtual OFVector<CodeSequenceMacro*>& getReasonForPerformedProcedureCodeSequence();
-
-  /** Set Study Instance UID
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (UI) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setStudyInstanceUID(const OFString &value,
-                                          const OFBool checkValue = OFTrue);
-
-  /** Set Study Date
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (DA) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setStudyDate(const OFString &value,
-                                    const OFBool checkValue = OFTrue);
-
-  /** set study time
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (TM) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setStudyTime(const OFString &value,
-                                    const OFBool checkValue = OFTrue);
-  /** Set Referring Physician's Name
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (PN) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setReferringPhysicianName(const OFString &value,
-                                                const OFBool checkValue = OFTrue);
-
-  /** Set Study ID
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (SH) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setStudyID(const OFString &value,
-                                  const OFBool checkValue = OFTrue);
-
-  /** Set Accession Number
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (SH) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setAccessionNumber(const OFString &value,
-                                          const OFBool checkValue = OFTrue);
-
-  /** Set Study Description
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setStudyDescription(const OFString &value,
-                                          const OFBool checkValue = OFTrue);
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     */
+    IODGeneralStudyModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
+    /** Constructor
+     */
+    IODGeneralStudyModule();
+
+    /** Destructor
+     */
+    virtual ~IODGeneralStudyModule();
+
+    /** Set missing values by inventing "default values". Automatically
+     *  called during write() by IODComponent.
+     */
+    virtual void inventMissing();
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of module
+     *  @return Name of the module ("GeneralStudyModule")
+     */
+    virtual OFString getName() const;
+
+    /** Clear (removes) all attributes handled by the modules of this component.
+     *  Rules are not reset.
+     */
+    virtual void clearData();
+
+    /** Read data into this module from given item
+     *  @param  source The item to read from
+     *  @param  clearOldData If OFTrue, old data in this module is cleared first (default: OFTrue)
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write this module to given item
+     *  @param  destination The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& destination);
+
+    /** Make sure that the module contains a Study Instance UID, i.e.\ a new one
+     *  is created if empty. An invalid UID is corrected if desired.
+     *  @param  correctInvalid Correct invalid UID if OFTrue, otherwise do nothing
+     */
+    virtual void ensureInstanceUID(const OFBool correctInvalid = OFFalse);
+
+    /** Get Study Instance UID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getStudyInstanceUID(OFString& value, const signed long pos = 0) const;
+
+    /** Get Study Date
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos   Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getStudyDate(OFString& value, const signed long pos = 0) const;
+
+    /** Get Study Time
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos  Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getStudyTime(OFString& value, const signed long pos = 0) const;
+
+    /** Get Referring Physician's Name
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getReferringPhysicianName(OFString& value, const signed long pos = 0) const;
+
+    /** Get Study ID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getStudyID(OFString& value, const signed long pos = 0) const;
+
+    /** Get Accession Number
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getAccessionNumber(OFString& value, const signed long pos = 0) const;
+
+    /** Get Study Description
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getStudyDescription(OFString& value, const signed long pos = 0) const;
+
+    /** Get reference to content of Issuer of Accession Number Sequence
+     *  @return Reference to single item of Issuer of Accession Number Sequence
+     */
+    virtual HL7HierarchicDesignatorMacro& getIssuerOfAccessionNumber();
+
+    /** Get reference to content of Procedure Code Sequence
+     *  @return Reference to items of Procedure Code Sequence
+     */
+    virtual OFVector<CodeSequenceMacro*>& getProcedureCodeSequence();
+
+    /** Get reference to content of Reason for Performed Procedure Code Sequence
+     *  @return Reference to items of Procedure Code Sequence
+     */
+    virtual OFVector<CodeSequenceMacro*>& getReasonForPerformedProcedureCodeSequence();
+
+    /** Set Study Instance UID
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (UI) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setStudyInstanceUID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Study Date
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (DA) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setStudyDate(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** set study time
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (TM) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setStudyTime(const OFString& value, const OFBool checkValue = OFTrue);
+    /** Set Referring Physician's Name
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (PN) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setReferringPhysicianName(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Study ID
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (SH) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setStudyID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Accession Number
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (SH) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setAccessionNumber(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Study Description
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setStudyDescription(const OFString& value, const OFBool checkValue = OFTrue);
 
 private:
+    /// Name of this module ("GeneralStudyModule")
+    static const OFString m_ModuleName;
 
-  /// Name of this module ("GeneralStudyModule")
-  static const OFString m_ModuleName;
-
-  /// Issuer of Accession Number Sequence
-  HL7HierarchicDesignatorMacro m_IssuerOfAccessionNumberSequence;
-
-  /// Procedure Code Sequence
-  OFVector<CodeSequenceMacro*> m_ProcedureCodeSequence;
+    /// Issuer of Accession Number Sequence
+    HL7HierarchicDesignatorMacro m_IssuerOfAccessionNumberSequence;
 
-  /// Reason for Performed Procedure Code Sequence
-  OFVector<CodeSequenceMacro*> m_ReasonForPerformedProcedureCodeSequence;
+    /// Procedure Code Sequence
+    OFVector<CodeSequenceMacro*> m_ProcedureCodeSequence;
 
+    /// Reason for Performed Procedure Code Sequence
+    OFVector<CodeSequenceMacro*> m_ReasonForPerformedProcedureCodeSequence;
 };
 
 #endif // MODGENERALSTUDY_H
index 5853f5061c40d41d91ee78d4f16dc6f5e87984d0..f7b228525c2509da93637de5ae88f2fdf79315e6 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -22,7 +22,7 @@
 #ifndef MODHELP_H
 #define MODHELP_H
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/ofstd/oftypes.h"
 
 #include "dcmtk/dcmiod/ioddef.h"
 class DcmTagKey;
 class DcmItem;
 
-
 /** This class contains helper functions that permit copying common modules
  *  from DICOM standard part 3 between DICOM datasets.
  *  @note The attribute lists per module are taken from the final text version
  *        of DICOM 2013.
  */
-class DCMTK_DCMIOD_EXPORT DcmModuleHelpers {
-
-  protected:
-
-    /// Generic copy module helper method.
-    template<size_t N>
-    static inline void copyModule(const DcmTagKey (&tags)[N],
-                                  DcmItem& src, DcmItem& dest);
+class DCMTK_DCMIOD_EXPORT DcmModuleHelpers
+{
+
+protected:
+    /** Generic copy module helper method.
+     *  @param  tags Reference of array with tags to be copied
+     *  @param  src  The source item to read the attributes from
+     *  @param  dest The target item to write the attributes to
+     */
+    template <size_t N>
+    static inline void copyModule(const DcmTagKey (&tags)[N], DcmItem& src, DcmItem& dest);
 
     /// List of tags within the Patient Module
     static const DcmTagKey patientModuleTags[];
@@ -79,8 +81,7 @@ class DCMTK_DCMIOD_EXPORT DcmModuleHelpers {
     /// List of tags within the General Image Module
     static const DcmTagKey generalImageModuleTags[];
 
-  public:
-
+public:
     /** Copy element defined by tag from source item to destination item.
      *  No in-depth search is performed but only the main level is searched
      *  for the given tag. If the tag is not found, the destination item
index 281edf59678ebf99300255389a365de732bce316..48a179e328ed15159fa4e7e72b2f2ad313d87470 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -23,8 +23,8 @@
 #define MODIMAGEPIXEL_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmiod/modimagepixelbase.h"
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmiod/modimagepixelbase.h"
 
 /** Class representing the Image Pixel Module:
  *
  *  Pixel Aspect Ratio: (IS,  2, 1C)
  *  ICC Profile: (OB, 1, 3)
  */
-template<typename T>
+template <typename T>
 class DCMTK_DCMIOD_EXPORT IODImagePixelModule : public IODImagePixelBase
 {
 
 public:
-
-  /// Data type of pixels
-  typedef T value_type;
-
-  static const DcmTagKey pixel_data_tag;
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  IODImagePixelModule(OFshared_ptr<DcmItem> item,
-                      OFshared_ptr<IODRules> rules);
-
-  /** Constructor
-   */
-  IODImagePixelModule();
-
-  /** Destructor
-   */
-  virtual ~IODImagePixelModule();
-
-  /** Read attributes from given item into this class
-   *  @param source  The source to read from
-   *  @param clearOldData If OFTrue, old data is cleared before reading. Otherwise
-   *         old data is overwritten (or amended)
-   *  @result EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write attributes from this class into given item
-   *  @param  destination The item to write to
-   *  @result EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& destination);
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of module
-   *  @return Name of the module ("ImagePixelModule")
-   */
-  virtual OFString getName() const;
-
-  /** Get pixel data type, always returns DataType::INTEGER for this class.
-   *  @return The data type of the pixel data
-   */
-  virtual DataType getDataType() const;
-
-   /** Get Bits Stored
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1)
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getBitsStored(Uint16& value,
-                                  const signed long pos = 0);
-
-  /** Get High Bit
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getHighBit(Uint16& value,
-                                 const signed long pos = 0);
-
-  /** Get Pixel Representation
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getPixelRepresentation(Uint16& value,
-                                             const signed long pos = 0);
-
-  /** Get Planar Configuration
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-  */
-  virtual OFCondition getPlanarConfiguration(Uint16& value,
-                                             const signed long pos = 0);
-
-  /** Get ICC Profile
-   *  @param  values Reference to variable in which the values should be stored
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getICCProfile(OFVector<Uint8>& values);
-
-  /** Set Samples per Pixel
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  checkValue Check 'value' for conformance with VR (US) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSamplesPerPixel(const Uint16 value,
-                                         const OFBool checkValue = OFTrue);
-
-  /** Set Photometric Interpretation
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPhotometricInterpretation(const OFString& value,
-                                                   const OFBool checkValue = OFTrue);
-
-  /** Set Bits Allocated
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setBitsAllocated(const Uint16 value,
-                                       const OFBool checkValue = OFTrue);
-
-  /** Set Bits Stored
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setBitsStored(const Uint16 value,
-                                    const OFBool checkValue = OFTrue);
-
-  /** Set High Bit
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setHighBit(const Uint16 value,
-                                 const OFBool checkValue = OFTrue);
-
-  /** Set Pixel Representation
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  checkValue Check 'value' for conformance with VR (US) and consistency
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPixelRepresentation(const Uint16 value,
-                                             const OFBool checkValue = OFTrue);
-
-  /** Set Planar Configuration
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  checkValue Check 'value' for conformance with VR (US) and consistency
-   *    with other attributes if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPlanarConfiguration(const Uint16 value,
-                                             const OFBool checkValue = OFTrue);
-
-  /** Set ICC Profile
-   *  @param  values Reference to variable in which the values should be stored
-   *  @param  length Length of array provided in values parameter
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setICCProfile(const Uint8* values,
-                                    const size_t length);
+    /// Data type of pixels
+    typedef T value_type;
+
+    static const DcmTagKey pixel_data_tag;
+
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     */
+    IODImagePixelModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
+
+    /** Constructor
+     */
+    IODImagePixelModule();
+
+    /** Destructor
+     */
+    virtual ~IODImagePixelModule();
+
+    /** Read attributes from given item into this class
+     *  @param source  The source to read from
+     *  @param clearOldData If OFTrue, old data is cleared before reading. Otherwise
+     *         old data is overwritten (or amended)
+     *  @result EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write attributes from this class into given item
+     *  @param  destination The item to write to
+     *  @result EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& destination);
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of module
+     *  @return Name of the module ("ImagePixelModule")
+     */
+    virtual OFString getName() const;
+
+    /** Get pixel data type, always returns DataType::INTEGER for this class.
+     *  @return The data type of the pixel data
+     */
+    virtual DataType getDataType() const;
+
+    /** Get Bits Stored
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getBitsStored(Uint16& value, const unsigned long pos = 0);
+
+    /** Get High Bit
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getHighBit(Uint16& value, const unsigned long pos = 0);
+
+    /** Get Pixel Representation
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPixelRepresentation(Uint16& value, const unsigned long pos = 0);
+
+    /** Get Planar Configuration
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPlanarConfiguration(Uint16& value, const unsigned long pos = 0);
+
+    /** Get ICC Profile
+     *  @param  values Reference to variable in which the values should be stored
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getICCProfile(OFVector<Uint8>& values);
+
+    /** Set Samples per Pixel
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  checkValue Check 'value' for conformance with VR (US) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSamplesPerPixel(const Uint16 value, const OFBool checkValue = OFTrue);
+
+    /** Set Photometric Interpretation
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPhotometricInterpretation(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Bits Allocated
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setBitsAllocated(const Uint16 value, const OFBool checkValue = OFTrue);
+
+    /** Set Bits Stored
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setBitsStored(const Uint16 value, const OFBool checkValue = OFTrue);
+
+    /** Set High Bit
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setHighBit(const Uint16 value, const OFBool checkValue = OFTrue);
+
+    /** Set Pixel Representation
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  checkValue Check 'value' for conformance with VR (US) and consistency
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPixelRepresentation(const Uint16 value, const OFBool checkValue = OFTrue);
+
+    /** Set Planar Configuration
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  checkValue Check 'value' for conformance with VR (US) and consistency
+     *    with other attributes if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPlanarConfiguration(const Uint16 value, const OFBool checkValue = OFTrue);
+
+    /** Set ICC Profile
+     *  @param  values Reference to variable in which the values should be stored
+     *  @param  length Length of array provided in values parameter
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setICCProfile(const Uint8* values, const size_t length);
 
 private:
-
-  /// This module's name ("ImagePixelModule")
-  static const OFString m_ModuleName;
-
+    /// This module's name ("ImagePixelModule")
+    static const OFString m_ModuleName;
 };
 
 #endif // MODIMAGEPIXEL_H
index 7455e020fc732c62dba50417df5f5b46928d6862..c1cc2dd7cdb237be8a2e704b093d26f3bf76fefc 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -15,7 +15,7 @@
  *
  *  Author: Michael Onken
  *
- *  Purpose: Base class for Image Pixel Module and related (e.g. Ploating Point)
+ *  Purpose: Base class for Image Pixel Module and related (e.g. Floating Point)
  *
  */
 
@@ -32,137 +32,124 @@ class DCMTK_DCMIOD_EXPORT IODImagePixelBase : public IODModule
 {
 
 public:
-
     enum DataType
     {
-      DATA_TYPE_UNKNOWN,
-      DATA_TYPE_FLOAT,
-      DATA_TYPE_DOUBLE,
-      DATA_TYPE_INTEGER
+        DATA_TYPE_UNKNOWN,
+        DATA_TYPE_FLOAT,
+        DATA_TYPE_DOUBLE,
+        DATA_TYPE_INTEGER
     };
 
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  IODImagePixelBase(OFshared_ptr<DcmItem> item,
-                    OFshared_ptr<IODRules> rules);
-
-  /** Constructor
-   */
-  IODImagePixelBase();
-
-  /** Destructor
-   */
-  virtual ~IODImagePixelBase();
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of module
-   *  @return Name of the module ("ImagePixelModule")
-   */
-  virtual OFString getName() const;
-
-  /** Get pixel data type
-   *  @return The data type of the pixel data
-   */
-  virtual DataType getDataType() const = 0;
-
-  // -------------------------------------------------------------------------
-  // Getters for all attribute that appear in all Image Pixel Modules
-  // -------------------------------------------------------------------------
-
-  /** Get Samples per Pixel
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getSamplesPerPixel(Uint16 &value,
-                                         const signed long pos = 0);
-
-  /** Get Photometric Interpretation
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-  */
-  virtual OFCondition getPhotometricInterpretation(OFString&value,
-                                                  const signed long pos = 0);
-
-  /** Get Rows
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getRows(Uint16& value,
-                              const signed long pos = 0);
-
-  /** Get Columns
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getColumns(Uint16& value,
-                                  const signed long pos = 0);
-
-  /** Get Bits Allocated
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getBitsAllocated(Uint16& value,
-                                       const signed long pos = 0);
-
-  /** Get Pixel Aspect Ratio
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-  */
-  virtual OFCondition getPixelAspectRatio(Uint16& value,
-                                          const signed long pos = 0);
-
-  // -------------------------------------------------------------------------
-  // Setters for all attribute that appear in all Image Pixel Modules and which
-  // do not have fixed values in sub classes.
-  // -------------------------------------------------------------------------
-
-  /** Set Rows
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRows(const Uint16 value,
-                              const OFBool checkValue = OFTrue);
-
-  /** Set Columns
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setColumns(const Uint16 value,
-                                 const OFBool checkValue = OFTrue);
-
-  /** Set Pixel Aspect Ratio
-   *  @param  verticalPixelSize The vertical pixel size (no unit)
-   *  @param  horizontalPixelSize The horizontal pixel size (no unit)
-   *  @param  checkValue Check 'value' for conformance with VR (IS)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPixelAspectRatio(const OFString& verticalPixelSize,
-                                          const OFString& horizontalPixelSize,
-                                          const OFBool checkValue = OFTrue);
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     */
+    IODImagePixelBase(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
+
+    /** Constructor
+     */
+    IODImagePixelBase();
+
+    /** Destructor
+     */
+    virtual ~IODImagePixelBase();
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of module
+     *  @return Name of the module ("ImagePixelModule")
+     */
+    virtual OFString getName() const;
+
+    /** Get pixel data type
+     *  @return The data type of the pixel data
+     */
+    virtual DataType getDataType() const = 0;
+
+    // -------------------------------------------------------------------------
+    // Getters for all attribute that appear in all Image Pixel Modules
+    // -------------------------------------------------------------------------
+
+    /** Get Samples per Pixel
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSamplesPerPixel(Uint16& value, const unsigned long pos = 0);
+
+    /** Get Photometric Interpretation
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPhotometricInterpretation(OFString& value, const signed long pos = 0);
+
+    /** Get Rows
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getRows(Uint16& value, const unsigned long pos = 0);
+
+    /** Get Columns
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getColumns(Uint16& value, const unsigned long pos = 0);
+
+    /** Get Bits Allocated
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getBitsAllocated(Uint16& value, const unsigned long pos = 0);
+
+    /** Get Pixel Aspect Ratio
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPixelAspectRatio(Uint16& value, const unsigned long pos = 0);
+
+    // -------------------------------------------------------------------------
+    // Setters for all attribute that appear in all Image Pixel Modules and which
+    // do not have fixed values in sub classes.
+    // -------------------------------------------------------------------------
+
+    /** Set Rows
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setRows(const Uint16 value, const OFBool checkValue = OFTrue);
+
+    /** Set Columns
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setColumns(const Uint16 value, const OFBool checkValue = OFTrue);
+
+    /** Set Pixel Aspect Ratio
+     *  @param  verticalPixelSize The vertical pixel size (no unit)
+     *  @param  horizontalPixelSize The horizontal pixel size (no unit)
+     *  @param  checkValue Check 'value' for conformance with VR (IS)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPixelAspectRatio(const OFString& verticalPixelSize,
+                                            const OFString& horizontalPixelSize,
+                                            const OFBool checkValue = OFTrue);
 
 private:
-
-  /// This module's name ("ImagePixelBase")
-  static const OFString m_ModuleName;
-
+    /// This module's name ("ImagePixelBase")
+    static const OFString m_ModuleName;
 };
 
 #endif // MODIMAGEPIXELBASE_H
index c4adb5459f5c51f5ad0942d7266bbc89afd536d5..f06a92eaa883a550baeb1336ebdc72653707de78 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016-2017, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 
 #include "dcmtk/config/osconfig.h"
 
-#include "dcmtk/ofstd/ofvriant.h"
 #include "dcmtk/dcmiod/modimagepixelbase.h"
-
+#include "dcmtk/ofstd/ofvriant.h"
 
 /** Visitor for returning base class of given Image Pixel Module
  */
 struct IODImagePixelVariantBaseVisitor
 {
 
-  /** Returns NULL since given argument is no pixel module at all
-   *  @return OFnullptr
-   */
-  IODImagePixelBase* operator()( OFmonostate& )
-  {
-    return OFnullptr;
-  }
-
-  /** Returns the base class pointer of all pixel modules
-   *  @param  base IODImagePixelBase pointer to given class instance
-   *  @return OFnullptr
-   */
-  IODImagePixelBase* operator()( IODImagePixelBase& base )
-  {
-    return &base;
-  }
+    /** Returns NULL since given argument is no pixel module at all
+     *  @return OFnullptr
+     */
+    IODImagePixelBase* operator()(OFmonostate&)
+    {
+        return OFnullptr;
+    }
+
+    /** Returns the base class pointer of all pixel modules
+     *  @param  base IODImagePixelBase pointer to given class instance
+     *  @return OFnullptr
+     */
+    IODImagePixelBase* operator()(IODImagePixelBase& base)
+    {
+        return &base;
+    }
 };
 
 /** Class representing different pixel modules from the DICOM standard:
@@ -56,226 +55,208 @@ struct IODImagePixelVariantBaseVisitor
  *  and the Double Floating Point Image Pixel module
  */
 #ifdef HAVE_CXX11
-template<typename... Types>
-class IODImagePixelVariant
-: public OFvariant<OFmonostate,Types...>
+template <typename... Types>
+class IODImagePixelVariant : public OFvariant<OFmonostate, Types...>
 #else
-template<OFVARIADIC_DECLARE_TEMPLATE_PARAMETER_PACK_WITH_DEFAULTS(T)>
-class IODImagePixelVariant
-: public OFvariant<OFmonostate,OFVARIADIC_TEMPLATE_PARAMETER_PACK(T)>
+template <OFVARIADIC_DECLARE_TEMPLATE_PARAMETER_PACK_WITH_DEFAULTS(T)>
+class IODImagePixelVariant : public OFvariant<OFmonostate, OFVARIADIC_TEMPLATE_PARAMETER_PACK(T)>
 #endif
 {
 
 public:
-
-  /** Constructor
-   */
-  IODImagePixelVariant()
-  : IODImagePixelVariant::variant()
-  {
-
-  }
-
-  /** Constructor, constructs pixel module based on given type
-   */
-  template<typename T>
-  IODImagePixelVariant(const T& t)
-  : IODImagePixelVariant::variant(t)
-  {
-
-  }
-
-  /** Destructor
-   */
-  ~IODImagePixelVariant()
-  {
-
-  }
-
-  /** Get name of module
-   *  @return Name of the actual module (e.g. "ImagePixelModule")
-   */
-  OFString getName() const
-  {
-    if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
-      return pBase->getName();
-    return OFString();
-  }
-
-  /** Get pixel data type
-   *  @return The data type of the pixel data
-   */
-  IODImagePixelBase::DataType getDataType() const
-  {
-    if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
-      return pBase->getDataType();
-    return IODImagePixelBase::DATA_TYPE_UNKNOWN;
-  }
-
-  /** Clear data (base class version)
-   */
-  void clearData()
-  {
-    if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
-      pBase->clearData();
-  }
-
-  // -------------------------------------------------------------------------
-  // Getters for all attribute that appear in all Image Pixel Modules
-  // -------------------------------------------------------------------------
-
-  /** Get Samples per Pixel
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  OFCondition getSamplesPerPixel(Uint16 &value,
-                                 const signed long pos = 0)
-  {
-    if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
-      return pBase->getSamplesPerPixel(value, pos);
-    return IOD_EC_InvalidPixelData;
-  }
-
-  /** Get Photometric Interpretation
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-  */
-  OFCondition getPhotometricInterpretation(OFString&value,
-                                           const signed long pos = 0)
-  {
-    if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
-      return pBase->getPhotometricInterpretation(value, pos);
-    return IOD_EC_InvalidPixelData;
-  }
-
-  /** Get Rows
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  OFCondition getRows(Uint16& value,
-                      const signed long pos = 0)
-  {
-    if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
-      return pBase->getRows(value, pos);
-    return IOD_EC_InvalidPixelData;
-  }
-
-  /** Get Columns
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  OFCondition getColumns(Uint16& value,
-                         const signed long pos = 0)
-  {
-    if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
-      return pBase->getColumns(value, pos);
-    return IOD_EC_InvalidPixelData;
-  }
-
-  /** Get Bits Allocated
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  OFCondition getBitsAllocated(Uint16& value,
-                               const signed long pos = 0)
-  {
-    if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
-      return pBase->getBitsAllocated(value, pos);
-    return IOD_EC_InvalidPixelData;
-  }
-
-  /** Get Pixel Aspect Ratio
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  OFCondition getPixelAspectRatio(Uint16& value,
-                                  const signed long pos = 0)
-  {
-    if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
-      return pBase->getPixelAspectRatio(value, pos);
-    return IOD_EC_InvalidPixelData;
-  }
-
-  // -------------------------------------------------------------------------
-  // Setters for all attribute that appear in all Image Pixel Modules and which
-  // do not have fixed values in sub classes.
-  // -------------------------------------------------------------------------
-
-  /** Set Rows
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  OFCondition setRows(const Uint16 value,
-                      const OFBool checkValue = OFTrue)
-  {
-    if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
-      return pBase->setRows(value, checkValue);
-    return IOD_EC_InvalidPixelData;
-
-  }
-
-  /** Set Columns
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  OFCondition setColumns(const Uint16 value,
-                         const OFBool checkValue = OFTrue)
-  {
-    if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
-      return pBase->setColumns(value, checkValue);
-    return IOD_EC_InvalidPixelData;
-
-  }
-
-  /** Set Pixel Aspect Ratio
-   *  @param  verticalPixelSize The vertical pixel size (no unit)
-   *  @param  horizontalPixelSize The horizontal pixel size (no unit)
-   *  @param  checkValue Check 'value' for conformance with VR (IS)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  OFCondition setPixelAspectRatio(const OFString& verticalPixelSize,
-                                  const OFString& horizontalPixelSize,
-                                  const OFBool checkValue = OFTrue)
-  {
-    if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
-      return pBase->setPixelAspectRatio(verticalPixelSize, horizontalPixelSize, checkValue);
-    return IOD_EC_InvalidPixelData;
-
-  }
-
-  /** Write pixel module base class data to given item
-   *  @param  dataset The item to write to (usually dataset level)
-   *  @return EC_Normal if successful, error otherwise
-   */
-  OFCondition write(DcmItem& dataset)
-  {
-    if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
-      return pBase->write(dataset);
-    return IOD_EC_InvalidPixelData;
-
-  }
-
-  /** Read pixel module base class data from given item
-   *  @param  dataset The item to read from (usually dataset level)
-   *  @return EC_Normal if successful, error otherwise
-   */
-  OFCondition read(DcmItem& dataset)
-  {
-    if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
-      return pBase->read(dataset);
-    return IOD_EC_InvalidPixelData;
-  }
-
+    /** Constructor
+     */
+    IODImagePixelVariant()
+        : IODImagePixelVariant::variant()
+    {
+    }
+
+    /** Constructor, constructs pixel module based on given type
+     *  @param  t The Image Pixel Module to be used
+     */
+    template <typename T>
+    IODImagePixelVariant(const T& t)
+        : IODImagePixelVariant::variant(t)
+    {
+    }
+
+    /** Destructor
+     */
+    ~IODImagePixelVariant()
+    {
+    }
+
+    /** Get name of module
+     *  @return Name of the actual module (e.g. "ImagePixelModule")
+     */
+    OFString getName() const
+    {
+        if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
+            return pBase->getName();
+        return OFString();
+    }
+
+    /** Get pixel data type
+     *  @return The data type of the pixel data
+     */
+    IODImagePixelBase::DataType getDataType() const
+    {
+        if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
+            return pBase->getDataType();
+        return IODImagePixelBase::DATA_TYPE_UNKNOWN;
+    }
+
+    /** Clear data (base class version)
+     */
+    void clearData()
+    {
+        if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
+            pBase->clearData();
+    }
+
+    // -------------------------------------------------------------------------
+    // Getters for all attribute that appear in all Image Pixel Modules
+    // -------------------------------------------------------------------------
+
+    /** Get Samples per Pixel
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    OFCondition getSamplesPerPixel(Uint16& value, const unsigned long pos = 0)
+    {
+        if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
+            return pBase->getSamplesPerPixel(value, pos);
+        return IOD_EC_InvalidPixelData;
+    }
+
+    /** Get Photometric Interpretation
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    OFCondition getPhotometricInterpretation(OFString& value, const signed long pos = 0)
+    {
+        if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
+            return pBase->getPhotometricInterpretation(value, pos);
+        return IOD_EC_InvalidPixelData;
+    }
+
+    /** Get Rows
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    OFCondition getRows(Uint16& value, const unsigned long pos = 0)
+    {
+        if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
+            return pBase->getRows(value, pos);
+        return IOD_EC_InvalidPixelData;
+    }
+
+    /** Get Columns
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    OFCondition getColumns(Uint16& value, const unsigned long pos = 0)
+    {
+        if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
+            return pBase->getColumns(value, pos);
+        return IOD_EC_InvalidPixelData;
+    }
+
+    /** Get Bits Allocated
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    OFCondition getBitsAllocated(Uint16& value, const unsigned long pos = 0)
+    {
+        if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
+            return pBase->getBitsAllocated(value, pos);
+        return IOD_EC_InvalidPixelData;
+    }
+
+    /** Get Pixel Aspect Ratio
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    OFCondition getPixelAspectRatio(Uint16& value, const unsigned long pos = 0)
+    {
+        if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
+            return pBase->getPixelAspectRatio(value, pos);
+        return IOD_EC_InvalidPixelData;
+    }
+
+    // -------------------------------------------------------------------------
+    // Setters for all attribute that appear in all Image Pixel Modules and which
+    // do not have fixed values in sub classes.
+    // -------------------------------------------------------------------------
+
+    /** Set Rows
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    OFCondition setRows(const Uint16 value, const OFBool checkValue = OFTrue)
+    {
+        if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
+            return pBase->setRows(value, checkValue);
+        return IOD_EC_InvalidPixelData;
+    }
+
+    /** Set Columns
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    OFCondition setColumns(const Uint16 value, const OFBool checkValue = OFTrue)
+    {
+        if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
+            return pBase->setColumns(value, checkValue);
+        return IOD_EC_InvalidPixelData;
+    }
+
+    /** Set Pixel Aspect Ratio
+     *  @param  verticalPixelSize The vertical pixel size (no unit)
+     *  @param  horizontalPixelSize The horizontal pixel size (no unit)
+     *  @param  checkValue Check 'value' for conformance with VR (IS)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    OFCondition setPixelAspectRatio(const OFString& verticalPixelSize,
+                                    const OFString& horizontalPixelSize,
+                                    const OFBool checkValue = OFTrue)
+    {
+        if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
+            return pBase->setPixelAspectRatio(verticalPixelSize, horizontalPixelSize, checkValue);
+        return IOD_EC_InvalidPixelData;
+    }
+
+    /** Write pixel module base class data to given item
+     *  @param  dataset The item to write to (usually dataset level)
+     *  @return EC_Normal if successful, error otherwise
+     */
+    OFCondition write(DcmItem& dataset)
+    {
+        if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
+            return pBase->write(dataset);
+        return IOD_EC_InvalidPixelData;
+    }
+
+    /** Read pixel module base class data from given item
+     *  @param  dataset The item to read from (usually dataset level)
+     *  @return EC_Normal if successful, error otherwise
+     */
+    OFCondition read(DcmItem& dataset)
+    {
+        if (IODImagePixelBase* pBase = OFvisit<IODImagePixelBase*>(IODImagePixelVariantBaseVisitor(), *this))
+            return pBase->read(dataset);
+        return IOD_EC_InvalidPixelData;
+    }
 };
 
 #endif // MODIMAGEPIXELBASE_H
index 83ff45ed5e93b6ada6dfd24b227287f48d7229b3..ac8fcd8a7cd2c10c96265686cc0c88652698821d 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -47,340 +47,312 @@ class DCMTK_DCMIOD_EXPORT IODMultiframeDimensionModule : public IODModule
 {
 
 public:
-
-  /** Helper class representing an item within the Dimension Index Sequence,
-   *  i.e.\ a single dimension description
-   */
-  class DimensionOrganizationItem : public IODComponent
-  {
-
-  public:
-
-    /** Constructor
-     *  @param  data The item to be used for data storage. If NULL, the
-     *          class creates an empty data container.
-     *  @param  rules The rule set for this class. If NULL, the class creates
-     *          one from scratch and adds its values.
-     *  @param  parent The parent of the IOD component (NULL if none or unknown)
-     */
-    DimensionOrganizationItem(OFshared_ptr<DcmItem> data,
-                              OFshared_ptr<IODRules> rules,
-                              IODComponent* parent);
-
-    /** Constructor
-     *  @param  parent The parent of the IOD component (NULL if none or unknown)
-     */
-    DimensionOrganizationItem(IODComponent* parent = NULL);
-
-    /** Destructor
-     */
-    virtual ~DimensionOrganizationItem();
-
-    /** Get name of module ("DimensionIndexPointerSequence")
-     *  @return Name of the module ("DimensionIndexPointerSequence")
-     */
-    virtual OFString getName() const;
-
-    /** Resets rules of this module to their original values
+    /** Helper class representing an item within the Dimension Index Sequence,
+     *  i.e.\ a single dimension description
      */
-    virtual void resetRules();
-
-    /** Get Dimension Organization UID
-     *  @param  value  Reference to variable in which the value should be
-     *          stored
-     *  @param  pos  Index of the value to get (0..vm-1), -1 for all components
-     *  @return EC_Normal if successful, an error code otherwise
+    class DCMTK_DCMIOD_EXPORT DimensionOrganizationItem : public IODComponent
+    {
+
+    public:
+        /** Constructor
+         *  @param  data The item to be used for data storage. If NULL, the
+         *          class creates an empty data container.
+         *  @param  rules The rule set for this class. If NULL, the class creates
+         *          one from scratch and adds its values.
+         *  @param  parent The parent of the IOD component (NULL if none or unknown)
+         */
+        DimensionOrganizationItem(OFshared_ptr<DcmItem> data, OFshared_ptr<IODRules> rules, IODComponent* parent);
+
+        /** Constructor
+         *  @param  parent The parent of the IOD component (NULL if none or unknown)
+         */
+        DimensionOrganizationItem(IODComponent* parent = NULL);
+
+        /** Destructor
+         */
+        virtual ~DimensionOrganizationItem();
+
+        /** Get name of module ("DimensionIndexPointerSequence")
+         *  @return Name of the module ("DimensionIndexPointerSequence")
+         */
+        virtual OFString getName() const;
+
+        /** Resets rules of this module to their original values
+         */
+        virtual void resetRules();
+
+        /** Get Dimension Organization UID
+         *  @param  value  Reference to variable in which the value should be
+         *          stored
+         *  @param  pos  Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition getDimensionOrganizationUID(OFString& value, const signed long pos = 0) const;
+
+        /** Set Dimension Organization UID
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value' for conformance with VR (PN) and VM (1) if enabled
+         *  @return status EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setDimensionOrganizationUID(const OFString& value, const OFBool checkValue = OFTrue);
+    };
+
+    /** Class representing a Dimension Index Pointer Sequence Item
+     *  managed by the Multi-frame Dimension Module
      */
-    virtual OFCondition getDimensionOrganizationUID(OFString &value,
-                                                    const signed long pos = 0) const;
-
-    /** Set Dimension Organization UID
-     *  @param  value Value to be set (single value only) or "" for no value
-     *  @param  checkValue Check 'value' for conformance with VR (PN) and VM (1) if enabled
-     *  @return status EC_Normal if successful, an error code otherwise
-     */
-    virtual OFCondition setDimensionOrganizationUID(const OFString& value,
-                                                    const OFBool checkValue = OFTrue);
-  };
-
-  /** Class representing a Dimension Index Pointer Sequence Item
-   *  managed by the Multi-frame Dimension Module
-   */
-  class DimensionIndexItem : public IODComponent
-  {
-
-  public:
+    class DimensionIndexItem : public IODComponent
+    {
+
+    public:
+        /** Constructor
+         *  @param  data The item to be used for data storage. If NULL, the
+         *          class creates an empty data container.
+         *  @param  rules The rule set for this class. If NULL, the class creates
+         *          one from scratch and adds its values.
+         *  @param  parent The parent of the IOD component (NULL if none or unknown)
+         */
+        DimensionIndexItem(OFshared_ptr<DcmItem> data, OFshared_ptr<IODRules> rules, IODComponent* parent);
+
+        /** Constructor
+         *  @param  parent The parent of the IOD component (NULL if none or unknown)
+         */
+        DimensionIndexItem(IODComponent* parent = NULL);
+
+        /** Destructor
+         */
+        virtual ~DimensionIndexItem();
+
+        /** Get name of module ("DimensionIndexSequence")
+         *  @return Name of the module ("[parent.]DimensionIndexSequence")
+         */
+        virtual OFString getName() const;
+
+        /** Resets rules to their original values
+         */
+        virtual void resetRules();
+
+        /** Get Dimension Index Pointer
+         *  @param  value  Reference to variable in which the value should be stored
+         *  @param  pos    Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition getDimensionIndexPointer(DcmTagKey& value, const signed long pos = 0) const;
+
+        /** Get Dimension Index Private Creator
+         *  @param  value  Reference to variable in which the value should be stored
+         *  @param  pos    Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition getDimensionIndexPrivateCreator(OFString& value, const signed long pos = 0) const;
+
+        /** Get Functional Group Pointer
+         *  @param  value  Reference to variable in which the value should be stored
+         *  @param  pos    Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition getFunctionalGroupPointer(DcmTagKey& value, const signed long pos = 0) const;
+
+        /** Get Functional Group Private Creator
+         *  @param  value  Reference to variable in which the value should be stored
+         *  @param  pos    Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition getFunctionalGroupPrivateCreator(OFString& value, const signed long pos = 0) const;
+
+        /** Get Dimension Organization UID
+         *  @param  value  Reference to variable in which the value should be stored
+         *  @param  pos    Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition getDimensionOrganizationUID(OFString& value, const signed long pos = 0) const;
+
+        /** Get Dimension Description Label
+         *  @param  value  Reference to variable in which the value should be stored
+         *  @param  pos    Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition getDimensionDescriptionLabel(OFString& value, const signed long pos = 0) const;
+
+        /** Set Dimension Index Pointer
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+         *          with other setter functions).
+         *  @return status EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setDimensionIndexPointer(const DcmTagKey& value, const OFBool checkValue = OFTrue);
+
+        /** Set Dimension Index Private Creator
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value' for conformance with VR (PN) and VM (1) if enabled
+         *  @return status EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setDimensionIndexPrivateCreator(const OFString& value, const OFBool checkValue = OFTrue);
+
+        /** Set Dimension Index Functional Group Pointer
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+         *          with other setter functions).
+         *  @return status EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setFunctionalGroupPointer(const DcmTagKey& value, const OFBool checkValue = OFTrue);
+
+        /** Set Dimension Index Functional Group Private Creator
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value. Not evaluated (here for consistency
+         *          with other setter functions).
+         *
+         *  @return status EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setFunctionalGroupPrivateCreator(const OFString& value, const OFBool checkValue = OFTrue);
+
+        /** Set Dimension Organization UID
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value' for conformance with VR and VM if enabled
+         *  @return status EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setDimensionOrganizationUID(const OFString& value, const OFBool checkValue = OFTrue);
+
+        /** Set Dimension Description Label
+         *  @param  value Value to be set (single value only) or "" for no value
+         *  @param  checkValue Check 'value' for conformance with VR and VM if enabled
+         *  @return status EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setDimensionDescriptionLabel(const OFString& value, const OFBool checkValue = OFTrue);
+    };
 
     /** Constructor
-     *  @param  data The item to be used for data storage. If NULL, the
+     *  @param  item The item to be used for data storage. If NULL, the
      *          class creates an empty data container.
      *  @param  rules The rule set for this class. If NULL, the class creates
      *          one from scratch and adds its values.
-     *  @param  parent The parent of the IOD component (NULL if none or unknown)
      */
-    DimensionIndexItem(OFshared_ptr<DcmItem> data,
-                       OFshared_ptr<IODRules> rules,
-                       IODComponent* parent);
+    IODMultiframeDimensionModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
 
     /** Constructor
-     *  @param  parent The parent of the IOD component (NULL if none or unknown)
      */
-    DimensionIndexItem(IODComponent* parent = NULL);
+    IODMultiframeDimensionModule();
 
     /** Destructor
      */
-    virtual ~DimensionIndexItem();
-
-    /** Get name of module ("DimensionIndexSequence")
-     *  @return Name of the module ("[parent.]DimensionIndexSequence")
-     */
-    virtual OFString getName() const;
-
-    /** Resets rules to their original values
+    virtual ~IODMultiframeDimensionModule();
+
+    /** Convenience method to add Dimension Index.
+     *  @param  dimensionIndexPointer The Dimension Index Pointer attribute
+     *  @param  dimensionOrganizationUID The Dimension Organization UID of the dimension organization
+     *          the pointer refers to. If UID does not exist yet (in the Dimension
+     *          Organization Sequence, it is created there automatically).
+     *  @param  functionalGroupPointer The functional group where the pointer attribute can be found
+     *  @param  dimensionDescriptionLabel The description label of this dimension (optional)
+     *  @param  dimensionIndexPrivateCreator The private creator of the Dimension Index Pointer
+     *          attribute. Required if dimensionIndexPointer points to a private attribute tag.
+     *  @param  functionalGroupPrivateCreator The private creator of the functional group. Required
+     *          if functionalGroupPointer points to a private attribute tag.
+     *  @return EC_Normal if index could be added, error otherwise (basic parameter checking)
+     *
      */
-    virtual void resetRules();
-
-    /** Get Dimension Index Pointer
-     *  @param  value  Reference to variable in which the value should be stored
-     *  @param  pos    Index of the value to get (0..vm-1), -1 for all components
-     *  @return EC_Normal if successful, an error code otherwise
+    virtual OFCondition addDimensionIndex(const DcmTagKey& dimensionIndexPointer,
+                                          const OFString& dimensionOrganizationUID,
+                                          const DcmTagKey& functionalGroupPointer,
+                                          const OFString& dimensionDescriptionLabel     = "",
+                                          const OFString& dimensionIndexPrivateCreator  = "",
+                                          const OFString& functionalGroupPrivateCreator = "");
+
+    /** Clear (removes) all attributes handled by the modules of this component.
+     *  Rules are not reset.
      */
-    virtual OFCondition getDimensionIndexPointer(DcmTagKey &value,
-                                                 const signed long pos = 0) const;
+    virtual void clearData();
 
-    /** Get Dimension Index Private Creator
-     *  @param  value  Reference to variable in which the value should be stored
-     *  @param  pos    Index of the value to get (0..vm-1), -1 for all components
-     *  @return EC_Normal if successful, an error code otherwise
+    /** Read data into this module from given item
+     *  @param  source The item to read from
+     *  @param  clearOldData If OFTrue, old data in this module is cleared first (default: OFTrue)
+     *  @return EC_Normal if reading was successful, error otherwise
      */
-    virtual OFCondition getDimensionIndexPrivateCreator(OFString& value,
-                                                        const signed long pos = 0) const;
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
 
-    /** Get Functional Group Pointer
-     *  @param  value  Reference to variable in which the value should be stored
-     *  @param  pos    Index of the value to get (0..vm-1), -1 for all components
-     *  @return EC_Normal if successful, an error code otherwise
+    /** Write this module to given item
+     *  @param  destination The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
      */
-    virtual OFCondition getFunctionalGroupPointer(DcmTagKey &value,
-                                                  const signed long pos = 0) const;
+    virtual OFCondition write(DcmItem& destination);
 
-    /** Get Functional Group Private Creator
-     *  @param  value  Reference to variable in which the value should be stored
-     *  @param  pos    Index of the value to get (0..vm-1), -1 for all components
-     *  @return EC_Normal if successful, an error code otherwise
+    /** Resets rules to their original values.
      */
-    virtual OFCondition getFunctionalGroupPrivateCreator(OFString &value,
-                                                         const signed long pos = 0) const;
+    virtual void resetRules();
 
-    /** Get Dimension Organization UID
-     *  @param  value  Reference to variable in which the value should be stored
-     *  @param  pos    Index of the value to get (0..vm-1), -1 for all components
-     *  @return EC_Normal if successful, an error code otherwise
+    /** Get name of module ("MultiframeDimensionModule")
+     *  @return Name of the module ("MultiframeDimensionModule")
      */
-    virtual OFCondition getDimensionOrganizationUID(OFString &value,
-                                                    const signed long pos = 0) const;
+    virtual OFString getName() const;
 
-    /** Get Dimension Description Label
+    /** Get Dimension Organization Type
      *  @param  value  Reference to variable in which the value should be stored
      *  @param  pos    Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getDimensionDescriptionLabel(OFString &value,
-                                                     const signed long pos = 0) const;
-
-    /** Set Dimension Index Pointer
-     *  @param  value Value to be set (single value only) or "" for no value
-     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-     *          with other setter functions).
-     *  @return status EC_Normal if successful, an error code otherwise
-     */
-    virtual OFCondition setDimensionIndexPointer(const DcmTagKey&value,
-                                                 const OFBool checkValue = OFTrue);
+    virtual OFCondition getDimensionOrganizationType(OFString& value, const signed long pos = 0) const;
 
-    /** Set Dimension Index Private Creator
+    /** Set Dimension Organization Type (Defined Terms as of DICOM 2014a "3D" and "3D_TEMPORAL")
      *  @param  value Value to be set (single value only) or "" for no value
-     *  @param  checkValue Check 'value' for conformance with VR (PN) and VM (1) if enabled
+     *  @param  checkValue Check 'value' for conformance with VR and VM if enabled
      *  @return status EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setDimensionIndexPrivateCreator(const OFString& value,
-                                                        const OFBool checkValue = OFTrue);
+    virtual OFCondition setDimensionOrganizationType(const OFString& value, const OFBool checkValue = OFTrue);
 
-    /** Set Dimension Index Functional Group Pointer
-     *  @param  value Value to be set (single value only) or "" for no value
-     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-     *          with other setter functions).
-     *  @return status EC_Normal if successful, an error code otherwise
+    /** Get content of the Dimension Index Sequence
+     *  @return Reference to the Dimension Index Pointer Sequence
      */
-    virtual OFCondition setFunctionalGroupPointer(const DcmTagKey& value,
-                                                  const OFBool checkValue = OFTrue);
+    virtual OFVector<DimensionIndexItem*>& getDimensionIndexSequence();
 
-    /** Set Dimension Index Functional Group Private Creator
-     *  @param  value Value to be set (single value only) or "" for no value
-     *  @param  checkValue Check 'value. Not evaluated (here for consistency
-     *          with other setter functions).
-     *
-     *  @return status EC_Normal if successful, an error code otherwise
+    /** Get content of the Dimension Organization Sequence
+     *  @return Reference to the Dimension Organization Sequence
      */
-    virtual OFCondition setFunctionalGroupPrivateCreator(const OFString& value,
-                                                         const OFBool checkValue = OFTrue);
-
-    /** Set Dimension Organization UID
-     *  @param  value Value to be set (single value only) or "" for no value
-     *  @param  checkValue Check 'value' for conformance with VR and VM if enabled
-     *  @return status EC_Normal if successful, an error code otherwise
+    virtual OFVector<DimensionOrganizationItem*>& getDimensionOrganizationSequence();
+
+    /** Check dimensions for consistency with functional groups. Note that one can provide
+     *  an item that provides the dataset containing the functional groups to check against.
+     *  This item must contain on main level the Shared and Per-frame Functional Group
+     *  Sequence. If no item is given (NULL pointer) it is tried to find these sequences
+     *  within "this" object which works in the case that this class was initialized with
+     *  an existing item (or the fg data was inserted in another way afterwards).
+     *  @param  fgItem The item containing functional group information
+     *  @return EC_Normal, if consistency is fine, error otherwise
      */
-    virtual OFCondition setDimensionOrganizationUID(const OFString& value,
-                                                    const OFBool checkValue = OFTrue);
-
-    /** Set Dimension Description Label
-     *  @param  value Value to be set (single value only) or "" for no value
-     *  @param  checkValue Check 'value' for conformance with VR and VM if enabled
-     *  @return status EC_Normal if successful, an error code otherwise
+    virtual OFCondition checkDimensions(DcmItem* fgItem = NULL);
+
+    /** Get specific index pointer element from per-frame functional group
+     *  sequence. Prints out error messages if index does not exist or
+     *  index location information provided by parameters is incomplete or invalid
+     *  @param  perFrameFG An instance of the Per-Frame Functional Group Sequence that
+     *          should be searched
+     *  @param  fgPointer The tag key of the functional group the value resides in
+     *  @param  indexPointer The tag of the dimension value inside the functional group
+     *  @param  fgPrivateCreator The private creator of the fgPointer tag key. Only required
+     *          if fgPointer is a private tag key (odd element number)
+     *  @param  privateCreator The private creator of the indexPointer tag key. Only required
+     *          if indexPointer is a private tag key (odd element number)
+     *  @return The element pointed to. If element could not be located, NULL is returned.
      */
-    virtual OFCondition setDimensionDescriptionLabel(const OFString& value,
-                                                     const OFBool checkValue = OFTrue);
-  };
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  IODMultiframeDimensionModule(OFshared_ptr<DcmItem> item,
-                               OFshared_ptr<IODRules> rules);
-
-  /** Constructor
-   */
-  IODMultiframeDimensionModule();
-
-  /** Destructor
-   */
-  virtual ~IODMultiframeDimensionModule();
-
-  /** Convenience method to add Dimension Index.
-   *  @param  dimensionIndexPointer The Dimension Index Pointer attribute
-   *  @param  dimensionOrganizationUID The Dimension Organization UID of the dimension organization
-   *          the pointer refers to. If UID does not exist yet (in the Dimension
-   *          Organization Sequence, it is created there automatically).
-   *  @param  functionalGroupPointer The functional group where the pointer attribute can be found
-   *  @param  dimensionDescriptionLabel The description label of this dimension (optional)
-   *  @param  dimensionIndexPrivateCreator The private creator of the Dimension Index Pointer
-   *          attribute. Required if dimensionIndexPointer points to a private attribute tag.
-   *  @param  functionalGroupPrivateCreator The private creator of the functional group. Required
-   *          if functionalGroupPointer points to a private attribute tag.
-   *  @return EC_Normal if index could be added, error otherwise (basic parameter checking)
-   *
-   */
-  virtual OFCondition addDimensionIndex(const DcmTagKey& dimensionIndexPointer,
-                                        const OFString&  dimensionOrganizationUID,
-                                        const DcmTagKey& functionalGroupPointer,
-                                        const OFString&  dimensionDescriptionLabel = "",
-                                        const OFString&  dimensionIndexPrivateCreator = "",
-                                        const OFString&  functionalGroupPrivateCreator = "");
-
-  /** Clear (removes) all attributes handled by the modules of this component.
-   *  Rules are not reset.
-   */
-  virtual void clearData();
-
-  /** Read data into this module from given item
-   *  @param  source The item to read from
-   *  @param  clearOldData If OFTrue, old data in this module is cleared first (default: OFTrue)
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& source,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write this module to given item
-   *  @param  destination The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& destination);
-
-  /** Resets rules to their original values.
-   */
-  virtual void resetRules();
-
-  /** Get name of module ("MultiframeDimensionModule")
-   *  @return Name of the module ("MultiframeDimensionModule")
-   */
-  virtual OFString getName() const;
-
-   /** Get Dimension Organization Type
-    *  @param  value  Reference to variable in which the value should be stored
-    *  @param  pos    Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getDimensionOrganizationType(OFString &value,
-                                                   const signed long pos = 0) const;
-
-  /** Set Dimension Organization Type (Defined Terms as of DICOM 2014a "3D" and "3D_TEMPORAL")
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR and VM if enabled
-   *  @return status EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setDimensionOrganizationType(const OFString &value,
-                                                   const OFBool checkValue = OFTrue);
-
-  /** Get content of the Dimension Index Sequence
-   *  @return Reference to the Dimension Index Pointer Sequence
-   */
-  virtual OFVector<DimensionIndexItem*>& getDimensionIndexSequence();
-
-  /** Get content of the Dimension Organization Sequence
-   *  @return Reference to the Dimension Organization Sequence
-   */
-  virtual OFVector<DimensionOrganizationItem*>& getDimensionOrganizationSequence();
-
-
-  /** Check dimensions for consistency with functional groups. Note that one can provide
-   *  an item that provides the dataset containing the functional groups to check against.
-   *  This item must contain on main level the Shared and Per-frame Functional Group
-   *  Sequence. If no item is given (NULL pointer) it is tried to find these sequences
-   *  within "this" object which works in the case that this class was initialized with
-   *  an existing item (or the fg data was inserted in another way afterwards).
-   *  @param  fgItem The item containing functional group information
-   *  @return EC_Normal, if consistency is fine, error otherwise
-   */
-  virtual OFCondition checkDimensions(DcmItem* fgItem = NULL);
-
-  /** Get specific index pointer element from per-frame functional group
-   *  sequence. Prints out error messages if index does not exist or
-   *  index location information provided by parameters is incomplete or invalid
-   *  @param  perFrameFG An instance of the Per-Frame Functional Group Sequence that
-   *          should be searched
-   *  @param  fgPointer The tag key of the functional group the value resides in
-   *  @param  indexPointer The tag of the dimension value inside the functional group
-   *  @param  fgPrivateCreator The private creator of the fgPointer tag key. Only required
-   *          if fgPointer is a private tag key (odd element number)
-   *  @param  privateCreator The private creator of the indexPointer tag key. Only required
-   *          if indexPointer is a private tag key (odd element number)
-   *  @return The element pointed to. If element could not be located, NULL is returned.
-   */
-  virtual DcmElement* getIndexElement(DcmSequenceOfItems* perFrameFG,
-                                      const DcmTagKey& fgPointer,
-                                      const DcmTagKey& indexPointer,
-                                      const OFString& fgPrivateCreator,
-                                      const OFString& privateCreator);
+    virtual DcmElement* getIndexElement(DcmSequenceOfItems* perFrameFG,
+                                        const DcmTagKey& fgPointer,
+                                        const DcmTagKey& indexPointer,
+                                        const OFString& fgPrivateCreator,
+                                        const OFString& privateCreator);
 
 protected:
-
-  /** Go over Dimension Index Pointers and extract Dimension Organization UIDs for
-   *  Dimension Organization Sequence.
-   */
-  void createDimensionOrganizationData();
+    /** Go over Dimension Index Pointers and extract Dimension Organization UIDs for
+     *  Dimension Organization Sequence.
+     */
+    void createDimensionOrganizationData();
 
 private:
+    /// This module's name (MultiframeDimensionModule)
+    static const OFString m_ModuleName;
 
-  /// This module's name (MultiframeDimensionModule)
-  static const OFString m_ModuleName;
-
-  /// Vector with all items of the Dimension Index Pointer Sequence
-  OFVector<DimensionIndexItem*> m_DimensionIndexSequence;
+    /// Vector with all items of the Dimension Index Pointer Sequence
+    OFVector<DimensionIndexItem*> m_DimensionIndexSequence;
 
-  /// Vector with all items of the Dimension Organization Sequence
-  OFVector<DimensionOrganizationItem*> m_DimensionOrganizationSequence;
+    /// Vector with all items of the Dimension Organization Sequence
+    OFVector<DimensionOrganizationItem*> m_DimensionOrganizationSequence;
 };
 
 #endif // MODMULTIFRAMEDIMENSION_H
index 213db6d82c85b85d4807b1bdcdd4fbe5efd485ff..65f79ee76335464427abd8178b5d5254e35bfa81 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define MODMULTIFRAMEFG_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmdata/dcsequen.h"
-#include "dcmtk/dcmdata/dcdeftag.h"
 #include "dcmtk/dcmdata/dcdatset.h"
-#include "dcmtk/dcmiod/iodrules.h"
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmdata/dcsequen.h"
 #include "dcmtk/dcmiod/ioddef.h"
+#include "dcmtk/dcmiod/iodrules.h"
 #include "dcmtk/dcmiod/modbase.h"
 
 /** Class managing the data from the Multi-Frame Functional Group Module. The
@@ -38,255 +38,250 @@ class DCMTK_DCMIOD_EXPORT IODMultiFrameFGModule : public IODModule
 {
 
 public:
-
-  // Forward declaration
-  class ConcatenationInfo;
-
-  /** Constructor
-   *  @param  data The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  IODMultiFrameFGModule(OFshared_ptr<DcmItem> data,
-                        OFshared_ptr<IODRules> rules);
-
-  /** Constructor
-   */
-  IODMultiFrameFGModule();
-
-  /** Virtual destructor
-   */
-  virtual ~IODMultiFrameFGModule();
-
-  /** Get name of the module ("MultiframeFunctionalGroupsModule")
-   *  @return Name of the module ("MultiframeFunctionalGroupsModule")
-   */
-  virtual OFString getName() const;
-
-  /** Reset attribute rules to their default values
-   */
-  virtual void resetRules();
-
-  // -- getters --
-
-  /** Get Instance Number
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getInstanceNumber(Sint32 &value,
-                                        const unsigned int pos = 0);
-
-   /** Get Content Date
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getContentDate(OFString &value,
-                                     const signed long pos = 0);
-
-   /** Get Content Time
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getContentTime(OFString &value,
-                                     const signed long pos = 0);
-
-   /** Get Number of Frames
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getNumberOfFrames(Sint32 &value,
-                                        const unsigned int pos = 0);
-
-   /** Get Representative Frame Number
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getRepresentativeFrameNumber(Uint16 &value,
-                                                   const unsigned int pos = 0);
-
-  /** Get Concatenation Information
-   *  @return Reference to the concatenation information
-   */
-  virtual ConcatenationInfo& getConcatenationInfo();
-
-   // -- setters --
-
-  /** Set Instance Number
-   *  @param  value Value to be stored
-   *  @param  checkValue Check 'value' for conformance with VR (IS) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setInstanceNumber(const OFString& value,
-                                        const OFBool checkValue = OFTrue);
-
-  /** Set Content Date
-   *  @param  value Value to be stored
-   *  @param  checkValue Check 'value' for conformance with VR (DA) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setContentDate(const OFString &value,
-                                     const OFBool checkValue = OFTrue);
-
-  /** Set Content Time
-   *  @param  value Value to be stored
-   *  @param  checkValue Check 'value' for conformance with VR (TM) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setContentTime(const OFString &value,
-                                     const OFBool checkValue = OFTrue);
-
-  /** Set Number of Frames
-   *  @param  value Value to be stored
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setNumberOfFrames(const Uint32 value);
-
-  /** Set Representative Frame Number
-   *  @param  value Value to be stored
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRepresentativeFrameNumber(const Uint16 value);
-
-  /** Set concatenation information
-   *  @param concatenationInfo The concatenation info to set
-   *  @return EC_Normal if successful, error otherwise
-   */
-  virtual OFCondition setConcatenationInfo(const ConcatenationInfo& concatenationInfo);
-
-  /** Helper class encapsulating concatenation information, including
-   *  Concatenation Frame Offset Number,
-   *  Concatenation UID,
-   *  SOP Instance UID of Concatenation Source,
-   *  In-concatenation Number,
-   *  In-concatenation Total Number
-   */
-  class DCMTK_DCMIOD_EXPORT ConcatenationInfo : public IODComponent
-  {
-
-  public:
+    // Forward declaration
+    class ConcatenationInfo;
 
     /** Constructor
      *  @param  data The item to be used for data storage. If NULL, the
      *          class creates an empty data container.
-     *  @param  rules The rule set where this classes rules are added to. If NULL, the
-     *          class creates an empty rule set.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
      */
-    ConcatenationInfo(OFshared_ptr<DcmItem> data,
-                      OFshared_ptr<IODRules> rules);
+    IODMultiFrameFGModule(OFshared_ptr<DcmItem> data, OFshared_ptr<IODRules> rules);
 
     /** Constructor
-     *  @param  parent The parent component of this class (if applicable, might be NULL)
      */
-    ConcatenationInfo(IODComponent* parent = NULL);
+    IODMultiFrameFGModule();
 
     /** Virtual destructor
      */
-    virtual ~ConcatenationInfo();
+    virtual ~IODMultiFrameFGModule();
+
+    /** Get name of the module ("MultiframeFunctionalGroupsModule")
+     *  @return Name of the module ("MultiframeFunctionalGroupsModule")
+     */
+    virtual OFString getName() const;
 
-    /** Resets attribute rules to their default values
+    /** Reset attribute rules to their default values
      */
     virtual void resetRules();
 
-    /** Get name of this component ("ConcatenationInfo")
+    /** Read attributes from given item into this class
+     *  @param source  The source to read from
+     *  @param clearOldData If OFTrue, old data is cleared before reading. Otherwise
+     *         old data is overwritten (or amended)
+     *  @result EC_Normal if reading was successful, error otherwise
      */
-    virtual OFString getName() const;
+    virtual OFCondition read(DcmItem& source, const OFBool clearOldData = OFTrue);
+
+    /** Write attributes from this class into given item
+     *  @param  destination The item to write to
+     *  @result EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& destination);
 
     // -- getters --
 
-    /** Get Concatenation Frame Offset Number
+    /** Get Instance Number
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    OFCondition getConcatenationFrameOffsetNumber(Uint32& value,
-                                                  const unsigned int pos);
+    virtual OFCondition getInstanceNumber(Sint32& value, const unsigned int pos = 0);
 
-    /** Get Concatenation UID
+    /** Get Content Date
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    OFCondition getConcatenationUID(OFString& value,
-                                    const signed long pos);
+    virtual OFCondition getContentDate(OFString& value, const signed long pos = 0);
 
-    /** Get SOP Instance UID of Concatenation Source
+    /** Get Content Time
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    OFCondition getSOPInstanceUIDOfConcatenationSource(OFString& value,
-                                                       const signed long pos);
+    virtual OFCondition getContentTime(OFString& value, const signed long pos = 0);
 
-    /** Get Concatenation Number
+    /** Get Number of Frames
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    OFCondition getInConcatenationNumber(Uint16& value,
-                                         const unsigned int pos);
+    virtual OFCondition getNumberOfFrames(Sint32& value, const unsigned int pos = 0);
 
-    /** Get Concatenation Total Number
+    /** Get Representative Frame Number
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    OFCondition getInConcatenationTotalNumber(Uint16& value,
-                                              const unsigned int pos);
+    virtual OFCondition getRepresentativeFrameNumber(Uint16& value, const unsigned int pos = 0);
+
+    /** Get Concatenation Information
+     *  @return Reference to the concatenation information
+     */
+    virtual ConcatenationInfo& getConcatenationInfo();
 
     // -- setters --
 
-    /** Set Concatenation Frame Offset Number
+    /** Set Instance Number
      *  @param  value Value to be stored
+     *  @param  checkValue Check 'value' for conformance with VR (IS) and VM (1) if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setConcatenationFrameOffsetNumber(const Uint32 value);
+    virtual OFCondition setInstanceNumber(const OFString& value, const OFBool checkValue = OFTrue);
 
-    /** Set Concatenation UID
+    /** Set Content Date
      *  @param  value Value to be stored
-     *  @param  checkValue If OFTrue, the value is checked for conformance
-     *          (VR = UID and VM = 1).
+     *  @param  checkValue Check 'value' for conformance with VR (DA) and VM (1) if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setConcatenationUID(const OFString &value,
-                                            const OFBool checkValue = OFTrue);
+    virtual OFCondition setContentDate(const OFString& value, const OFBool checkValue = OFTrue);
 
-    /** Set SOP Instance UID of Concatenation Source
+    /** Set Content Time
      *  @param  value Value to be stored
-     *  @param  checkValue If OFTrue, the value is checked for conformance
-     *          (VR = UID and VM = 1).
+     *  @param  checkValue Check 'value' for conformance with VR (TM) and VM (1) if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setSOPInstanceUIDOfConcatenationSource(const OFString &value,
-                                                               const OFBool checkValue = OFTrue);
+    virtual OFCondition setContentTime(const OFString& value, const OFBool checkValue = OFTrue);
 
-    /** Set In-concatenation Number
+    /** Set Number of Frames
      *  @param  value Value to be stored
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setInConcatenationNumber(const Uint16 value);
+    virtual OFCondition setNumberOfFrames(const Uint32 value);
 
-    /** Set In-concatenation Total Number
+    /** Set Representative Frame Number
      *  @param  value Value to be stored
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setInConcatenationTotalNumber(const Uint16 value);
-
-  }; // ConcatenationInfoClass
+    virtual OFCondition setRepresentativeFrameNumber(const Uint16 value);
 
+    /** Set concatenation information
+     *  @param concatenationInfo The concatenation info to set
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition setConcatenationInfo(const ConcatenationInfo& concatenationInfo);
+
+    /** Helper class encapsulating concatenation information, including
+     *  Concatenation Frame Offset Number,
+     *  Concatenation UID,
+     *  SOP Instance UID of Concatenation Source,
+     *  In-concatenation Number,
+     *  In-concatenation Total Number
+     */
+    class DCMTK_DCMIOD_EXPORT ConcatenationInfo : public IODComponent
+    {
+
+    public:
+        /** Constructor
+         *  @param  data The item to be used for data storage. If NULL, the
+         *          class creates an empty data container.
+         *  @param  rules The rule set where this classes rules are added to. If NULL, the
+         *          class creates an empty rule set.
+         */
+        ConcatenationInfo(OFshared_ptr<DcmItem> data, OFshared_ptr<IODRules> rules);
+
+        /** Constructor
+         *  @param  parent The parent component of this class (if applicable, might be NULL)
+         */
+        ConcatenationInfo(IODComponent* parent = NULL);
+
+        /** Virtual destructor
+         */
+        virtual ~ConcatenationInfo();
+
+        /** Resets attribute rules to their default values
+         */
+        virtual void resetRules();
+
+        /** Get name of this component ("ConcatenationInfo")
+         *  @return Name of this component
+         */
+        virtual OFString getName() const;
+
+        // -- getters --
+
+        /** Get Concatenation Frame Offset Number
+         *  @param  value Reference to variable in which the value should be stored
+         *  @param  pos Index of the value to get (0..vm-1)
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        OFCondition getConcatenationFrameOffsetNumber(Uint32& value, const unsigned int pos = 0);
+
+        /** Get Concatenation UID
+         *  @param  value Reference to variable in which the value should be stored
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        OFCondition getConcatenationUID(OFString& value, const signed long pos = -1);
+
+        /** Get SOP Instance UID of Concatenation Source
+         *  @param  value Reference to variable in which the value should be stored
+         *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        OFCondition getSOPInstanceUIDOfConcatenationSource(OFString& value, const signed long pos = -1);
+
+        /** Get Concatenation Number
+         *  @param  value Reference to variable in which the value should be stored
+         *  @param  pos Index of the value to get (0..vm-1)
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        OFCondition getInConcatenationNumber(Uint16& value, const unsigned int pos = 0);
+
+        /** Get Concatenation Total Number
+         *  @param  value Reference to variable in which the value should be stored
+         *  @param  pos Index of the value to get (0..vm-1)
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        OFCondition getInConcatenationTotalNumber(Uint16& value, const unsigned int pos = 0);
+
+        // -- setters --
+
+        /** Set Concatenation Frame Offset Number
+         *  @param  value Value to be stored
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setConcatenationFrameOffsetNumber(const Uint32 value);
+
+        /** Set Concatenation UID
+         *  @param  value Value to be stored
+         *  @param  checkValue If OFTrue, the value is checked for conformance
+         *          (VR = UID and VM = 1).
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setConcatenationUID(const OFString& value, const OFBool checkValue = OFTrue);
+
+        /** Set SOP Instance UID of Concatenation Source
+         *  @param  value Value to be stored
+         *  @param  checkValue If OFTrue, the value is checked for conformance
+         *          (VR = UID and VM = 1).
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setSOPInstanceUIDOfConcatenationSource(const OFString& value,
+                                                                   const OFBool checkValue = OFTrue);
+
+        /** Set In-concatenation Number
+         *  @param  value Value to be stored
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setInConcatenationNumber(const Uint16 value);
+
+        /** Set In-concatenation Total Number
+         *  @param  value Value to be stored
+         *  @return EC_Normal if successful, an error code otherwise
+         */
+        virtual OFCondition setInConcatenationTotalNumber(const Uint16 value);
+
+    }; // ConcatenationInfoClass
 
 private:
+    /// Concatenation Information
+    ConcatenationInfo m_ConcatenationInfo;
 
-  /// Concatenation Information
-  ConcatenationInfo m_ConcatenationInfo;
-
-  /// Module name ("MultiframeFunctionalGroupsModule"
-  static const OFString m_ModuleName;
+    /// Module name ("MultiframeFunctionalGroupsModule"
+    static const OFString m_ModuleName;
 };
 
 #endif // MODMULTIFRAMEFG_H
index 3e9422cc74f859ac3c46a63dc1e91f1b6f5d5ab4..af4dbf89016b2712371a55a9097110c4f0d671e0 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define MODPATIENT_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofmem.h"
-#include "dcmtk/ofstd/ofvector.h"
 #include "dcmtk/dcmdata/dctk.h"
 #include "dcmtk/dcmiod/iodrules.h"
 #include "dcmtk/dcmiod/modbase.h"
+#include "dcmtk/ofstd/ofmem.h"
+#include "dcmtk/ofstd/ofvector.h"
 
 /** Class representing the Patient Module:
 *
 * Patient's Name: (PN, 1, 2)
 * Patient ID: (LO, 1, 2)
 * Patient's Birth Date: (DA, 1, 2)
 * Patient's Sex: (CS, 1, 2)
 */
+ *
+ * Patient's Name: (PN, 1, 2)
+ * Patient ID: (LO, 1, 2)
+ * Patient's Birth Date: (DA, 1, 2)
+ * Patient's Sex: (CS, 1, 2)
+ */
 class DCMTK_DCMIOD_EXPORT IODPatientModule : public IODModule
 {
 
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  IODPatientModule(OFshared_ptr<DcmItem> item,
-                   OFshared_ptr<IODRules> rules);
-
-  /** Constructor
-   */
-  IODPatientModule();
-
-  /** Destructor
-   */
-  virtual ~IODPatientModule();
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of module ("PatientModule")
-   *  @return Name of the module ("PatientModule")
-   */
-  virtual OFString getName() const;
-
-   /** Get Patient's Name
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getPatientName(OFString &value,
-                                     const signed long pos = 0) const;
-
-  /** Get Patient ID
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getPatientID(OFString &value,
-                                    const signed long pos = 0) const;
-
-   /** Get Patient's Birth Date
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getPatientBirthDate(OFString &value,
-                                          const signed long pos = 0) const;
-
-   /** Get Patient's Sex
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getPatientSex(OFString &value,
-                                    const signed long pos = 0) const;
-
-
-  /** Set Patient's Name
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (PN) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPatientName(const OFString &value,
-                                     const OFBool checkValue = OFTrue);
-
-  /** Set Patient ID
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPatientID(const OFString &value,
-                                   const OFBool checkValue = OFTrue);
-
-  /** Set Patient's Birth Date
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (DA) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPatientBirthDate(const OFString &value,
-                                          const OFBool checkValue = OFTrue);
-
-  /** Set Patient's Sex
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPatientSex(const OFString &value,
-                                    const OFBool checkValue = OFTrue);
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     */
+    IODPatientModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
+
+    /** Constructor
+     */
+    IODPatientModule();
+
+    /** Destructor
+     */
+    virtual ~IODPatientModule();
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of module ("PatientModule")
+     *  @return Name of the module ("PatientModule")
+     */
+    virtual OFString getName() const;
+
+    /** Get Patient's Name
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPatientName(OFString& value, const signed long pos = 0) const;
+
+    /** Get Patient ID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPatientID(OFString& value, const signed long pos = 0) const;
+
+    /** Get Patient's Birth Date
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPatientBirthDate(OFString& value, const signed long pos = 0) const;
+
+    /** Get Patient's Sex
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPatientSex(OFString& value, const signed long pos = 0) const;
+
+    /** Set Patient's Name
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (PN) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPatientName(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Patient ID
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPatientID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Patient's Birth Date
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (DA) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPatientBirthDate(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Patient's Sex
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPatientSex(const OFString& value, const OFBool checkValue = OFTrue);
 
 private:
-
-  /// The name of this module ("PatientModule")
-  static const OFString m_ModuleName;
+    /// The name of this module ("PatientModule")
+    static const OFString m_ModuleName;
 };
 
 #endif // MODPATIENT_H
index 11181e26905dd15121ae1bed5d49d922517a304b..1f0ddf4e2793aa4dc1d355be3d3091fe463109a5 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define MODPATIENTSTUDY_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofmem.h"
-#include "dcmtk/ofstd/ofoption.h"
-#include "dcmtk/ofstd/ofvector.h"
 #include "dcmtk/dcmdata/dctk.h"
 #include "dcmtk/dcmiod/iodrules.h"
 #include "dcmtk/dcmiod/modbase.h"
+#include "dcmtk/ofstd/ofmem.h"
+#include "dcmtk/ofstd/ofoption.h"
+#include "dcmtk/ofstd/ofvector.h"
 
 /** Class representing the Patient Study Module:
 *
 * Admitting Diagnoses Description: (LO, 1-n, 3)
 * Patient's Age: (AS, 1, 3)
 * Patient's Size: (DS, 1, 3)
 * Patient's Weight: (DS,1, 3)
 */
+ *
+ * Admitting Diagnoses Description: (LO, 1-n, 3)
+ * Patient's Age: (AS, 1, 3)
+ * Patient's Size: (DS, 1, 3)
+ * Patient's Weight: (DS,1, 3)
+ */
 class DCMTK_DCMIOD_EXPORT IODPatientStudyModule : public IODModule
 {
 
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  IODPatientStudyModule(OFshared_ptr<DcmItem> item,
-                        OFshared_ptr<IODRules> rules);
-
-  /** Constructor
-   */
-  IODPatientStudyModule();
-
-  /** Destructor
-   */
-  virtual ~IODPatientStudyModule();
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of module ("PatientStudyModule")
-   *  @return Name of the module ("PatientStudyModule")
-   */
-  virtual OFString getName() const;
-
-   /** Get Admitting Diagnoses Description
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getAdmittingDiagnosesDescription(OFString& value,
-                                                       const signed long pos = 0) const;
-
-  /** Get Patient's Age (string as defined by VR "AS", see DICOM part 5)
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getPatientAge(OFString &value,
-                                    const signed long pos = 0) const;
-
-  /** Get Patient's Weight (in kilograms)
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getPatientWeight(Float64 &value,
-                                       const unsigned long pos = 0) const;
-
-  /** Get Patient's Size (in meters)
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getPatientSize(Float64 &value,
-                                     const unsigned long pos = 0) const;
-
-  /** Set Admitting Diagnoses Description
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1-n)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setAdmittingDiagnosesDescription(const OFString &value,
-                                                       const OFBool checkValue = OFTrue);
-
-  /** Set Patient's Age (formatted as defined by VR "AS", see part 5 of the standard)
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (AS) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPatientAge(const OFString &value,
-                                    const OFBool checkValue = OFTrue);
-
-  /** Set Patient's Size (in meters)
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1)
-   *         if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPatientSize(const OFString &value,
-                                     const OFBool checkValue = OFTrue);
-
-  /** Set Patient's Weight (in kilograms)
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPatientWeight(const OFString &value,
-                                       const OFBool checkValue = OFTrue);
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     */
+    IODPatientStudyModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
+
+    /** Constructor
+     */
+    IODPatientStudyModule();
+
+    /** Destructor
+     */
+    virtual ~IODPatientStudyModule();
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of module ("PatientStudyModule")
+     *  @return Name of the module ("PatientStudyModule")
+     */
+    virtual OFString getName() const;
+
+    /** Get Admitting Diagnoses Description
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getAdmittingDiagnosesDescription(OFString& value, const signed long pos = 0) const;
+
+    /** Get Patient's Age (string as defined by VR "AS", see DICOM part 5)
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPatientAge(OFString& value, const signed long pos = 0) const;
+
+    /** Get Patient's Weight (in kilograms)
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPatientWeight(Float64& value, const unsigned long pos = 0) const;
+
+    /** Get Patient's Size (in meters)
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPatientSize(Float64& value, const unsigned long pos = 0) const;
+
+    /** Set Admitting Diagnoses Description
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1-n)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setAdmittingDiagnosesDescription(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Patient's Age (formatted as defined by VR "AS", see part 5 of the standard)
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (AS) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPatientAge(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Patient's Size (in meters)
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1)
+     *         if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPatientSize(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Patient's Weight (in kilograms)
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (DS) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPatientWeight(const OFString& value, const OFBool checkValue = OFTrue);
 
 private:
-
-  /// The name of this module ("PatientStudyModule")
-  static const OFString m_ModuleName;
+    /// The name of this module ("PatientStudyModule")
+    static const OFString m_ModuleName;
 };
 
 #endif // MODPATIENT_H
index 901825d2e16f5bcb9e6c5e260c620ee41f9d09c3..5b263e3cf454fe6ad9b64109b970b90b66b4a855 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define MODSEGMENTATIONSERIES_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofmem.h"
-#include "dcmtk/ofstd/ofvector.h"
 #include "dcmtk/dcmdata/dctk.h"
 #include "dcmtk/dcmiod/modbase.h"
+#include "dcmtk/ofstd/ofmem.h"
+#include "dcmtk/ofstd/ofvector.h"
 
 /** Class representing the Segmentation Series Module:
  *
@@ -40,102 +40,91 @@ class DCMTK_DCMIOD_EXPORT IODSegmentationSeriesModule : public IODModule
 {
 
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  IODSegmentationSeriesModule(OFshared_ptr<DcmItem> item,
-                              OFshared_ptr<IODRules> rules);
-  /** Constructor
-   */
-  IODSegmentationSeriesModule();
-
-  /** Destructor
-   */
-  virtual ~IODSegmentationSeriesModule();
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of this module
-   *  @return Name of the module ("SegmentationSeriesModule")
-   */
-  virtual OFString getName() const;
-
-   /** Get Modality (always returns "SEG")
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getModality(OFString &value,
-                                  const signed long pos = 0) const;
-
-   /** Get Series Number
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getSeriesNumber(OFString &value,
-                                      const signed long pos = 0) const;
-
-   /** Get Referenced PPS SOP Class UID
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getPPSSOPClassUID(OFString &value,
-                                        const signed long pos = 0) const;
-
-   /** Get Referenced PPS SOP Instance UID
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getPPSSOPInstanceUID(OFString &value,
-                                           const signed long pos = 0) const;
-
-  /** Set Series Number
-   *  @param  value Value to be set (single value only).  If an empty string is passed,
-   *          the value "1" is set when displaying or writing the document since
-   *          the corresponding DICOM attribute is mandatory.
-   *  @param  checkValue Check 'value' for conformance with VR (IS) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSeriesNumber(const OFString &value,
-                                      const OFBool checkValue = OFTrue);
-
-  /** Set Referenced PPS SOP Class UID
-   *  @param  value Value to be set (single value only).  If an empty string is passed,
-   *          the value "1" is set when displaying or writing the document since
-   *          the corresponding DICOM attribute is mandatory.
-   *  @param  checkValue Check 'value' for conformance with VR (IS) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPPSSOPClassUID(const OFString &value,
-                                        const OFBool checkValue = OFTrue);
-
-  /** Set Referenced PPS SOP Instance UID
-   *  @param  value Value to be set (single value only).  If an empty string is passed,
-   *          the value "1" is set when displaying or writing the document since
-   *          the corresponding DICOM attribute is mandatory.
-   *  @param  checkValue Check 'value' for conformance with VR (IS) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPPSSOPInstanceUID(const OFString &value,
-                                           const OFBool checkValue = OFTrue);
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     */
+    IODSegmentationSeriesModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
+    /** Constructor
+     */
+    IODSegmentationSeriesModule();
+
+    /** Destructor
+     */
+    virtual ~IODSegmentationSeriesModule();
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of this module
+     *  @return Name of the module ("SegmentationSeriesModule")
+     */
+    virtual OFString getName() const;
+
+    /** Get Modality (always returns "SEG")
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getModality(OFString& value, const signed long pos = 0) const;
+
+    /** Get Series Number
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSeriesNumber(OFString& value, const signed long pos = 0) const;
+
+    /** Get Referenced PPS SOP Class UID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPPSSOPClassUID(OFString& value, const signed long pos = 0) const;
+
+    /** Get Referenced PPS SOP Instance UID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPPSSOPInstanceUID(OFString& value, const signed long pos = 0) const;
+
+    /** Set Series Number
+     *  @param  value Value to be set (single value only).  If an empty string is passed,
+     *          the value "1" is set when displaying or writing the document since
+     *          the corresponding DICOM attribute is mandatory.
+     *  @param  checkValue Check 'value' for conformance with VR (IS) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSeriesNumber(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Referenced PPS SOP Class UID
+     *  @param  value Value to be set (single value only).  If an empty string is passed,
+     *          the value "1" is set when displaying or writing the document since
+     *          the corresponding DICOM attribute is mandatory.
+     *  @param  checkValue Check 'value' for conformance with VR (IS) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPPSSOPClassUID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Referenced PPS SOP Instance UID
+     *  @param  value Value to be set (single value only).  If an empty string is passed,
+     *          the value "1" is set when displaying or writing the document since
+     *          the corresponding DICOM attribute is mandatory.
+     *  @param  checkValue Check 'value' for conformance with VR (IS) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPPSSOPInstanceUID(const OFString& value, const OFBool checkValue = OFTrue);
 
 private:
-
-  /// Name of this module ("SegmentationSeriesModule")
-  static const OFString m_ModuleName;
-
+    /// Name of this module ("SegmentationSeriesModule")
+    static const OFString m_ModuleName;
 };
 
 #endif // MODSEGMENTATIONSERIES_H
index ef99908cbf40aca0e554bb8466e7e721c3669ec9..fab033e3fa86b0fc663ea3cdee126b97c475f349 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define MODSOPCOMMON_H
 
 #include "dcmtk/config/osconfig.h"
+#include "dcmtk/dcmiod/modbase.h"
 #include "dcmtk/ofstd/ofcond.h"
 #include "dcmtk/ofstd/ofstring.h"
-#include "dcmtk/dcmiod/modbase.h"
-
 
 /** Class representing the SOP Common Module. Supported Attributes:
 *
 * SOP Class UID: (UI, 1, 1)
 * SOP Instance UID: (UI, 1, 1)
 * Specific Character Set: (CS, 1-n, 1C)
 * Instance Creation Date: (DA, 1, 3)
 * Instance Creation Time: (TM, 1, 3)
 * Instance Creator UID: (UI, 1, 3)
 * Timezone Offset from UTC: (SH, 1, 3)
 *
 */
+ *
+ * SOP Class UID: (UI, 1, 1)
+ * SOP Instance UID: (UI, 1, 1)
+ * Specific Character Set: (CS, 1-n, 1C)
+ * Instance Creation Date: (DA, 1, 3)
+ * Instance Creation Time: (TM, 1, 3)
+ * Instance Creator UID: (UI, 1, 3)
+ * Timezone Offset from UTC: (SH, 1, 3)
+ *
+ */
 class DCMTK_DCMIOD_EXPORT IODSOPCommonModule : public IODModule
 {
 
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  IODSOPCommonModule(OFshared_ptr<DcmItem> item,
-                     OFshared_ptr<IODRules> rules);
-
-  /** Constructor
-   */
-  IODSOPCommonModule();
-
-  /** Destructor
-   */
-  virtual ~IODSOPCommonModule();
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Set missing values by inventing "default values". Automatically
-   *  called during write() by IODComponent.
-   */
-  virtual void inventMissing();
-
-  /** Get name of module
-   *  @return Name of the module ("SOPCommonModule")
-   */
-  virtual OFString getName() const;
-
-  /** Make sure that the module contains a SOP Instance UID, i.e.\ a new one
-   *  is created if empty. An invalid UID is corrected if desired.
-   *  @param  correctInvalid Correct invalid UID if OFTrue, otherwise do nothing
-   */
-  virtual void ensureInstanceUID(const OFBool correctInvalid = OFFalse);
-
-   /** Get SOP Class UID
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getSOPClassUID(OFString &value,
-                                      const signed long pos = 0) const;
-
-   /** Get SOP Instance UID
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getSOPInstanceUID(OFString &value,
-                                        const signed long pos = 0) const;
-
-   /** Get Instance Creator UID
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getInstanceCreatorUID(OFString &value,
-                                            const signed long pos = 0) const;
-
-   /** Get Timeho e Offset from UTC
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getTimezoneOffsetFromUTC(OFString &value,
-                                               const signed long pos = 0) const;
-
-   /** Get Specific Character Set
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getSpecificCharacterSet(OFString &value,
-                                              const signed long pos = 0) const;
-
-   /** Get Instance Creation Date
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getInstanceCreationDate(OFString &value,
-                                              const signed long pos = 0) const;
-
-   /** Get Instance Creation Time
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
-    */
-  virtual OFCondition getInstanceCreationTime(OFString &value,
-                                              const signed long pos = 0) const;
-
-  /** Set SOP Instance UID
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (UI) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSOPInstanceUID(const OFString &value,
-                                        const OFBool checkValue = OFTrue);
-
-  /** Set SOP Class UID
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (UI) and
-   *           VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSOPClassUID(const OFString &value,
-                                     const OFBool checkValue = OFTrue);
-
-  /**  Set Specific Character Set. The internal enumerated value is set accordingly.
-   *   Please note that code extensions techniques are not supported. Therefore, only
-   *   a single value can be passed.
-   *   @param  value Value to be set (single value only) or "" for no value
-   *   @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
-   *   @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSpecificCharacterSet(const OFString &value,
-                                              const OFBool checkValue = OFTrue);
-
-  /** Set Instance Creation Date
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (TM) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setInstanceCreationDate(const OFString &value,
-                                              const OFBool checkValue = OFTrue);
-  /** Set Instance Creation Date
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (TM) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setInstanceCreationTime(const OFString &value,
-                                              const OFBool checkValue = OFTrue);
-
-  /**  Set Instance Creator UID
-   *   @param  value Value to be set (single value only) or "" for no value
-   *   @param  checkValue Check 'value' for conformance with VR (UID) and VM (1)
-   *           if enabled
-   *   @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setInstanceCreatorUID(const OFString &value,
-                                            const OFBool checkValue = OFTrue);
-
-  /**  Set Timezone Offset From UTC
-   *   @param  value Value to be set (single value only) or "" for no value.
-   *   Encoded as an ASCII string in the format “&ZZXX”. The components of this
-   *   string, from left to right, are & = “+” or “-”, and ZZ = Hours and
-   *   XX = Minutes of offset.
-   *   @param  checkValue Check 'value' for conformance with VR (SH) and VM (1) if enabled
-   *   @return EC_Normal if successful, an error code otherwise
-   */  virtual OFCondition setTimeZoneOffsetFromUTC(const OFString &value,
-                                                    const OFBool checkValue = OFTrue) const;
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     */
+    IODSOPCommonModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
+
+    /** Constructor
+     */
+    IODSOPCommonModule();
+
+    /** Destructor
+     */
+    virtual ~IODSOPCommonModule();
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Set missing values by inventing "default values". Automatically
+     *  called during write() by IODComponent.
+     */
+    virtual void inventMissing();
+
+    /** Get name of module
+     *  @return Name of the module ("SOPCommonModule")
+     */
+    virtual OFString getName() const;
+
+    /** Make sure that the module contains a SOP Instance UID, i.e.\ a new one
+     *  is created if empty. An invalid UID is corrected if desired.
+     *  @param  correctInvalid Correct invalid UID if OFTrue, otherwise do nothing
+     */
+    virtual void ensureInstanceUID(const OFBool correctInvalid = OFFalse);
+
+    /** Get SOP Class UID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSOPClassUID(OFString& value, const signed long pos = 0) const;
+
+    /** Get SOP Instance UID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSOPInstanceUID(OFString& value, const signed long pos = 0) const;
+
+    /** Get Instance Creator UID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getInstanceCreatorUID(OFString& value, const signed long pos = 0) const;
+
+    /** Get Timeho e Offset from UTC
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getTimezoneOffsetFromUTC(OFString& value, const signed long pos = 0) const;
+
+    /** Get Specific Character Set
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSpecificCharacterSet(OFString& value, const signed long pos = 0) const;
+
+    /** Get Instance Creation Date
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getInstanceCreationDate(OFString& value, const signed long pos = 0) const;
+
+    /** Get Instance Creation Time
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getInstanceCreationTime(OFString& value, const signed long pos = 0) const;
+
+    /** Set SOP Instance UID
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (UI) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSOPInstanceUID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set SOP Class UID
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (UI) and
+     *           VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSOPClassUID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /**  Set Specific Character Set. The internal enumerated value is set accordingly.
+     *   Please note that code extensions techniques are not supported. Therefore, only
+     *   a single value can be passed.
+     *   @param  value Value to be set (single value only) or "" for no value
+     *   @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
+     *   @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSpecificCharacterSet(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Instance Creation Date
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (TM) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setInstanceCreationDate(const OFString& value, const OFBool checkValue = OFTrue);
+    /** Set Instance Creation Date
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (TM) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setInstanceCreationTime(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /**  Set Instance Creator UID
+     *   @param  value Value to be set (single value only) or "" for no value
+     *   @param  checkValue Check 'value' for conformance with VR (UID) and VM (1)
+     *           if enabled
+     *   @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setInstanceCreatorUID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /**  Set Timezone Offset From UTC
+     *   @param  value Value to be set (single value only) or "" for no value.
+     *   Encoded as an ASCII string in the format “&ZZXX”. The components of this
+     *   string, from left to right, are & = “+” or “-”, and ZZ = Hours and
+     *   XX = Minutes of offset.
+     *   @param  checkValue Check 'value' for conformance with VR (SH) and VM (1) if enabled
+     *   @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setTimeZoneOffsetFromUTC(const OFString& value, const OFBool checkValue = OFTrue) const;
 
 private:
-
-  /// Name of this module ("SOPCommonModule")
-  static const OFString m_ModuleName;
-
+    /// Name of this module ("SOPCommonModule")
+    static const OFString m_ModuleName;
 };
 
 #endif // MODSOPCOMMON_H
index 7a46b007f0e3c5be624231f85627b4ee72a76e2e..cef7ea836b1880c8abf42a8fd3201190a36b41d2 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2017, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -23,8 +23,8 @@
 #define MODSYNCHRONIZATION_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofoption.h"
 #include "dcmtk/dcmiod/modbase.h"
+#include "dcmtk/ofstd/ofoption.h"
 
 /** Class representing the Synchronization Module:
  *
@@ -41,15 +41,13 @@ class DCMTK_DCMIOD_EXPORT IODSynchronizationModule : public IODModule
 {
 
 public:
-
     /** Constructor
      *  @param  item The item to be used for data storage. If NULL, the
      *          class creates an empty data container.
      *  @param  rules The rule set for this class. If NULL, the class creates
      *          one from scratch and adds its values.
      */
-    IODSynchronizationModule(OFshared_ptr<DcmItem> item,
-                             OFshared_ptr<IODRules> rules);
+    IODSynchronizationModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
 
     /** Constructor
      */
@@ -69,32 +67,29 @@ public:
     virtual OFString getName() const;
 
     /** Get Synchronization Frame of Reference UID
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getSynchronizationFrameOfReferenceUID(OFString& value,
-                                                              const signed long pos = 0) const;
+    virtual OFCondition getSynchronizationFrameOfReferenceUID(OFString& value, const signed long pos = 0) const;
 
     /** Get Synchronization Trigger
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getSynchronizationTrigger(OFString& value,
-                                                  const signed long pos = 0) const;
+    virtual OFCondition getSynchronizationTrigger(OFString& value, const signed long pos = 0) const;
 
     /** Get Trigger Source or Type
-    *  @param  value Reference to variable in which the value should be stored
-    *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-    *  @return EC_Normal if successful, an error code otherwise
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getTriggerSourceOrType(OFString& value,
-                                               const signed long pos = 0) const;
+    virtual OFCondition getTriggerSourceOrType(OFString& value, const signed long pos = 0) const;
 
     /** Get Synchronization Channel
-    *  @param  value Reference to variable in which the value should be stored
-    *  @return EC_Normal if successful, an error code otherwise
+     *  @param  value Reference to variable in which the value should be stored
+     *  @return EC_Normal if successful, an error code otherwise
      */
     virtual OFCondition getSynchronizationChannel(OFVector<Uint16>& value) const;
 
@@ -103,32 +98,28 @@ public:
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getAcquisitionTimeSynchronized(OFString& value,
-                                                       const signed long pos = 0) const;
+    virtual OFCondition getAcquisitionTimeSynchronized(OFString& value, const signed long pos = 0) const;
 
     /** Get Time Source
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getTimeSource(OFString& value,
-                                      const signed long pos = 0) const;
+    virtual OFCondition getTimeSource(OFString& value, const signed long pos = 0) const;
 
     /** Get Time Distribution Protocol
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getTimeDistributionProtocol(OFString& value,
-                                                    const signed long pos = 0) const;
+    virtual OFCondition getTimeDistributionProtocol(OFString& value, const signed long pos = 0) const;
 
     /** Get NTP Source Address
      *  @param  value Reference to variable in which the value should be stored
      *  @param  pos Index of the value to get (0..vm-1), -1 for all components
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition getNTPSourceAddress(OFString& value,
-                                            const signed long pos = 0) const;
+    virtual OFCondition getNTPSourceAddress(OFString& value, const signed long pos = 0) const;
 
     /** Set Synchronization Frame of Reference UID
      *  @param  value Value to be set
@@ -136,8 +127,7 @@ public:
      *          if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setSynchronizationFrameofReferenceUID(const OFString &value,
-                                                              const OFBool checkValue = OFTrue);
+    virtual OFCondition setSynchronizationFrameofReferenceUID(const OFString& value, const OFBool checkValue = OFTrue);
 
     /** Set Synchronization Trigger
      *  @param  value Value to be set
@@ -145,8 +135,7 @@ public:
      *          if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setSynchronizationTrigger(const OFString &value,
-                                                  const OFBool checkValue = OFTrue);
+    virtual OFCondition setSynchronizationTrigger(const OFString& value, const OFBool checkValue = OFTrue);
 
     /** Set Trigger Source or Type
      *  @param  value Value to be set
@@ -154,8 +143,7 @@ public:
      *          if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setTriggerSourceOrType(const OFString &value,
-                                               const OFBool checkValue = OFTrue);
+    virtual OFCondition setTriggerSourceOrType(const OFString& value, const OFBool checkValue = OFTrue);
 
     /** Set Synchronization Channel
      *  @param  value Value to be set
@@ -163,7 +151,7 @@ public:
      *          with other setter functions).
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setSynchronizationChannel(const OFPair<Uint16, Uint16> &value,
+    virtual OFCondition setSynchronizationChannel(const OFPair<Uint16, Uint16>value,
                                                   const OFBool checkValue = OFTrue);
 
     /** Set Acquisition Time Synchronized
@@ -172,8 +160,7 @@ public:
      *          if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setAcquisitionTimeSynchronized(const OFString &value,
-                                                       const OFBool checkValue = OFTrue);
+    virtual OFCondition setAcquisitionTimeSynchronized(const OFString& value, const OFBool checkValue = OFTrue);
 
     /** Set Time Source
      *  @param  value Value to be set
@@ -181,8 +168,7 @@ public:
      *          if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setTimeSource(const OFString &value,
-                                      const OFBool checkValue = OFTrue);
+    virtual OFCondition setTimeSource(const OFString& value, const OFBool checkValue = OFTrue);
 
     /** Set Time Distribution Protocol
      *  @param  value Value to be set
@@ -190,8 +176,7 @@ public:
      *          if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setTimeDistributionProtocol(const OFString &value,
-                                                    const OFBool checkValue = OFTrue);
+    virtual OFCondition setTimeDistributionProtocol(const OFString& value, const OFBool checkValue = OFTrue);
 
     /** Set NTP Source Address
      *  @param  value Value to be set
@@ -199,37 +184,33 @@ public:
      *          if enabled
      *  @return EC_Normal if successful, an error code otherwise
      */
-    virtual OFCondition setNTPSourceAddress(const OFString &value,
-                                            const OFBool checkValue = OFTrue);
+    virtual OFCondition setNTPSourceAddress(const OFString& value, const OFBool checkValue = OFTrue);
 
 protected:
+    /** Check whether given string is a valid value for attribute
+     *  Acquisition Time Synchronized
+     *  @param  value The value to check
+     *  @return OFTrue if value is valid for this attribute, OFFalse otherwise
+     */
+    virtual OFBool isValidAcquisitionTimeSynchronized(const OFString& value);
 
-  /** Check whether given string is a valid value for attribute
-   *  Acquisition Time Synchronized
-   *  @param  value The value to check
-   *  @return OFTrue if value is valid for this attribute, OFFalse otherwise
-   */
-  virtual OFBool isValidAcquisitionTimeSynchronized(const OFString& value);
-
-  /** Check whether given string is a valid value for attribute
-   *  Time Distribution Protocol
-   *  @param  value The value to check
-   *  @return OFTrue if value is valid for this attribute, OFFalse otherwise
-   */
-  virtual OFBool isValidTimeDistributionProtocol(const OFString& value);
-
-  /** Check whether given string is a valid value for attribute
-   *  Synchronization Trigger
-   *  @param  value The value to check
-   *  @return OFTrue if value is valid for this attribute, OFFalse otherwise
-   */
-  virtual OFBool isValidSynchronizationTrigger(const OFString& value);
+    /** Check whether given string is a valid value for attribute
+     *  Time Distribution Protocol
+     *  @param  value The value to check
+     *  @return OFTrue if value is valid for this attribute, OFFalse otherwise
+     */
+    virtual OFBool isValidTimeDistributionProtocol(const OFString& value);
 
-private:
+    /** Check whether given string is a valid value for attribute
+     *  Synchronization Trigger
+     *  @param  value The value to check
+     *  @return OFTrue if value is valid for this attribute, OFFalse otherwise
+     */
+    virtual OFBool isValidSynchronizationTrigger(const OFString& value);
 
+private:
     /// Module name "SynchronizationModule"
     static const OFString m_ModuleName;
-
 };
 
 #endif // MODSYNCHRONIZATION_H
index 5cde76460da22520cb9bc181aa0b9533b976be1a..ef2d55f7cdd41c7a7fa16dbfd74cc685b679d0bc 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -23,8 +23,8 @@
 #define MODUSFOR_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofoption.h"
 #include "dcmtk/dcmiod/modbase.h"
+#include "dcmtk/ofstd/ofoption.h"
 
 /** Class representing the Frame of Reference Module:
  *
@@ -42,188 +42,170 @@ class DCMTK_DCMIOD_EXPORT IODUSFoRModule : public IODModule
 {
 
 public:
-
-  /** Constructor
-   *  @param  item The item to be used for data storage. If NULL, the
-   *          class creates an empty data container.
-   *  @param  rules The rule set for this class. If NULL, the class creates
-   *          one from scratch and adds its values.
-   */
-  IODUSFoRModule(OFshared_ptr<DcmItem> item,
-                 OFshared_ptr<IODRules> rules);
-
-  /** Constructor
-   */
-  IODUSFoRModule();
-
-  /** Destructor
-   */
-  virtual ~IODUSFoRModule();
-
-  /** Resets rules to their original values
-   */
-  virtual void resetRules();
-
-  /** Get name of module
-   *  @return Name of the module ("UltrasoundFrameOfReferenceModule")
-   */
-  virtual OFString getName() const;
-
-  /** Get Volume Frame of Reference UID
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getVolumeFrameOfReferenceUID(OFString& value,
-                                                   const signed long pos = 0) const;
-
-  /** Get Position Reference Indicator
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getUltrasoundAcquisitionGeometry(OFString& value,
-                                                       const signed long pos = 0) const;
-
-  /** Get Apex Position
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getApexPosition(Float64& value,
-                                      const unsigned long pos = 0) const;
-
-  /** Get Apex Position
-   *  @param  value Reference to variable in which the value should be stored
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getApexPosition(OFVector<Float64>& value);
-
-  /** Get Volume to Transducer Relationship
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getVolumetoTransducerRelationship(OFString& value,
-                                                        const signed long pos = 0);
-
-  /** Get Volume to Table Mapping Matrix
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getVolumetoTransducerMappingMatrix(Float64& value,
-                                                         const signed long pos = 0) const;
-
-  /** Get Volume to Table Mapping Matrix
-   *  @param  value Reference to variable in which the value should be stored
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getVolumetoTransducerMappingMatrix(OFVector<Float64>& value);
-
-  /** Get Patient Frame of Reference Source
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getPatientFrameofReferenceSource(OFString& value,
-                                                       const signed long pos = 0);
-
-  /** Get Table Frame of Reference UID
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getTableFrameofReferenceUID(OFString& value,
-                                                  const signed long pos = 0);
-
-  /** Get Volume to Table Mapping Matrix
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getVolumetoTableMappingMatrix(Float64& value,
-                                                    const signed long pos = 0) const;
-
-  /** Get Volume to Table Mapping Matrix
-   *  @param  value Reference to variable in which the value should be stored
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getVolumetoTableMappingMatrix(OFVector<Float64>& value);
-
-  /** Set Volume Frame Of Reference UID
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance with VR (UI) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setVolumeFrameOfReferenceUID(const OFString &value,
-                                                   const OFBool checkValue = OFTrue);
-
-  /** Set Ultrasound Acquisition Geometry
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setUltrasoundAcquisitionGeometry(const OFString &value,
-                                                       const OFBool checkValue = OFTrue);
-
-  /** Set Apex Position
-   *  @param  xValue xValue to be set
-   *  @param  yValue yValue to be set
-   *  @param  zValue zValue to be set
-   *  @param  checkValue Does nothing at the moment
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setApexPosition(const Float64& xValue,
-                                      const Float64& yValue,
-                                      const Float64& zValue,
-                                      const OFBool checkValue = OFTrue);
-
-  /** Set Volume to Transducer Relationship
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setVolumetoTransducerRelationship(const OFString &value,
-                                                        const OFBool checkValue = OFTrue);
-
-  /** Set Volume to Transducer Mapping Matrix
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance with VR (FD) and VM (16) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setVolumetoTransducerMappingMatrix(const OFVector<Float64>& value,
-                                                         const OFBool checkValue = OFTrue);
-
-  /** Set Patient Frame of Reference Source
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setPatientFrameOfReferenceSource(const OFString &value,
-                                                       const OFBool checkValue = OFTrue);
-
-  /** Set Table Frame of Reference UID
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance with VR (UI) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setTableFrameofReferenceUID(const OFString &value,
-                                                  const OFBool checkValue = OFTrue);
-
-  /** Set Volume to Table Mapping Matrix
-   *  @param  value Value to be set
-   *  @param  checkValue Check 'value' for conformance with VR (FD) and VM (16) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setVolumeToTableMappingMatrix(const OFVector<Float64>& value,
-                                                    const OFBool checkValue = OFTrue);
+    /** Constructor
+     *  @param  item The item to be used for data storage. If NULL, the
+     *          class creates an empty data container.
+     *  @param  rules The rule set for this class. If NULL, the class creates
+     *          one from scratch and adds its values.
+     */
+    IODUSFoRModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules);
+
+    /** Constructor
+     */
+    IODUSFoRModule();
+
+    /** Destructor
+     */
+    virtual ~IODUSFoRModule();
+
+    /** Resets rules to their original values
+     */
+    virtual void resetRules();
+
+    /** Get name of module
+     *  @return Name of the module ("UltrasoundFrameOfReferenceModule")
+     */
+    virtual OFString getName() const;
+
+    /** Get Volume Frame of Reference UID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getVolumeFrameOfReferenceUID(OFString& value, const signed long pos = 0) const;
+
+    /** Get Position Reference Indicator
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getUltrasoundAcquisitionGeometry(OFString& value, const signed long pos = 0) const;
+
+    /** Get Apex Position
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getApexPosition(Float64& value, const unsigned long pos = 0) const;
+
+    /** Get Apex Position
+     *  @param  value Reference to variable in which the value should be stored
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getApexPosition(OFVector<Float64>& value);
+
+    /** Get Volume to Transducer Relationship
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getVolumetoTransducerRelationship(OFString& value, const signed long pos = 0);
+
+    /** Get Volume to Table Mapping Matrix
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getVolumetoTransducerMappingMatrix(Float64& value, const unsigned long pos = 0) const;
+
+    /** Get Volume to Table Mapping Matrix
+     *  @param  value Reference to variable in which the value should be stored
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getVolumetoTransducerMappingMatrix(OFVector<Float64>& value);
+
+    /** Get Patient Frame of Reference Source
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getPatientFrameofReferenceSource(OFString& value, const signed long pos = 0);
+
+    /** Get Table Frame of Reference UID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getTableFrameofReferenceUID(OFString& value, const signed long pos = 0);
+
+    /** Get Volume to Table Mapping Matrix
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getVolumetoTableMappingMatrix(Float64& value, const unsigned long pos = 0) const;
+
+    /** Get Volume to Table Mapping Matrix
+     *  @param  value Reference to variable in which the value should be stored
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getVolumetoTableMappingMatrix(OFVector<Float64>& value);
+
+    /** Set Volume Frame Of Reference UID
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance with VR (UI) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setVolumeFrameOfReferenceUID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Ultrasound Acquisition Geometry
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setUltrasoundAcquisitionGeometry(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Apex Position
+     *  @param  xValue xValue to be set
+     *  @param  yValue yValue to be set
+     *  @param  zValue zValue to be set
+     *  @param  checkValue Does nothing at the moment
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setApexPosition(const Float64& xValue,
+                                        const Float64& yValue,
+                                        const Float64& zValue,
+                                        const OFBool checkValue = OFTrue);
+
+    /** Set Volume to Transducer Relationship
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setVolumetoTransducerRelationship(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Volume to Transducer Mapping Matrix
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance with VR (FD) and VM (16) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setVolumetoTransducerMappingMatrix(const OFVector<Float64>& value,
+                                                           const OFBool checkValue = OFTrue);
+
+    /** Set Patient Frame of Reference Source
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance with VR (CS) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setPatientFrameOfReferenceSource(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Table Frame of Reference UID
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance with VR (UI) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setTableFrameofReferenceUID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Volume to Table Mapping Matrix
+     *  @param  value Value to be set
+     *  @param  checkValue Check 'value' for conformance with VR (FD) and VM (16) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setVolumeToTableMappingMatrix(const OFVector<Float64>& value, const OFBool checkValue = OFTrue);
 
 private:
-
-  /// Module name "UltrasoundFrameOfReferenceModule"
-  static const OFString m_ModuleName;
-
+    /// Module name "UltrasoundFrameOfReferenceModule"
+    static const OFString m_ModuleName;
 };
 
 #endif // MODUSFOR_H
index a7cbbde6e559e99d8029528a0cc9fd04953a1cb3..954c7d0e777573046d8124e9b28d5597f5622bbc 100644 (file)
@@ -1,28 +1,23 @@
-cielabutil.o: cielabutil.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmiod/cielabutil.h \
- ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+cielabutil.o: cielabutil.cc ../include/dcmtk/dcmiod/cielabutil.h \
+ ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/ioddef.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
- ../../ofstd/include/dcmtk/ofstd/ofexport.h
-iodcommn.o: iodcommn.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmiod/iodcommn.h ../include/dcmtk/dcmiod/iodrules.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h
+iodcommn.o: iodcommn.cc ../include/dcmtk/dcmiod/iodcommn.h \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../include/dcmtk/dcmiod/iodtypes.h \
+ ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/ioddef.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
@@ -35,6 +30,9 @@ iodcommn.o: iodcommn.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -45,8 +43,10 @@ iodcommn.o: iodcommn.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmiod/modpatient.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../include/dcmtk/dcmiod/modcommoninstanceref.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
@@ -123,24 +123,22 @@ iodcommn.o: iodcommn.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmiod/modbase.h \
+ ../include/dcmtk/dcmiod/iodmacro.h ../include/dcmtk/dcmiod/modbase.h \
+ ../include/dcmtk/dcmiod/iodreferences.h \
+ ../include/dcmtk/dcmiod/modequipment.h ../include/dcmtk/dcmiod/modfor.h \
+ ../include/dcmtk/dcmiod/modgeneralseries.h \
+ ../include/dcmtk/dcmiod/modgeneralstudy.h \
+ ../include/dcmtk/dcmiod/modpatient.h \
  ../include/dcmtk/dcmiod/modpatientstudy.h \
  ../../ofstd/include/dcmtk/ofstd/ofoption.h \
  ../../ofstd/include/dcmtk/ofstd/ofalign.h \
- ../include/dcmtk/dcmiod/modgeneralstudy.h \
- ../include/dcmtk/dcmiod/iodmacro.h \
- ../include/dcmtk/dcmiod/modequipment.h \
- ../include/dcmtk/dcmiod/modgeneralseries.h \
- ../include/dcmtk/dcmiod/modfor.h ../include/dcmtk/dcmiod/modsopcommon.h \
- ../include/dcmtk/dcmiod/modcommoninstanceref.h \
- ../include/dcmtk/dcmiod/iodreferences.h \
- ../include/dcmtk/dcmiod/iodutil.h \
+ ../include/dcmtk/dcmiod/modsopcommon.h ../include/dcmtk/dcmiod/iodutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
 iodcontentitemmacro.o: iodcontentitemmacro.cc \
  ../../config/include/dcmtk/config/osconfig.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
@@ -186,41 +184,37 @@ iodcontentitemmacro.o: iodcontentitemmacro.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../ofstd/include/dcmtk/ofstd/oftime.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
- ../include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../include/dcmtk/dcmiod/iodcontentitemmacro.h \
+ ../include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmiod/iodcontentitemmacro.h \
- ../include/dcmtk/dcmiod/modbase.h ../include/dcmtk/dcmiod/iodmacro.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -256,26 +250,30 @@ iodcontentitemmacro.o: iodcontentitemmacro.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
- ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h
-iodmacro.o: iodmacro.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmiod/iodmacro.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
- ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
- ../../ofstd/include/dcmtk/ofstd/ofcast.h \
- ../../ofstd/include/dcmtk/ofstd/ofexport.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmiod/iodrules.h ../include/dcmtk/dcmiod/iodtypes.h \
+ ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/modbase.h \
+ ../include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
+iodmacro.o: iodmacro.cc ../include/dcmtk/dcmiod/iodmacro.h \
+ ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
@@ -373,33 +371,43 @@ iodmacro.o: iodmacro.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
  ../include/dcmtk/dcmiod/iodrules.h ../include/dcmtk/dcmiod/iodtypes.h \
- ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmiod/modbase.h ../include/dcmtk/dcmiod/iodutil.h \
+ ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/modbase.h \
+ ../include/dcmtk/dcmiod/iodutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
-iodreferences.o: iodreferences.cc \
+iodreferences.o: iodreferences.cc ../include/dcmtk/dcmiod/iodreferences.h \
  ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmiod/iodtypes.h \
- ../../oflog/include/dcmtk/oflog/oflog.h \
- ../../oflog/include/dcmtk/oflog/logger.h \
- ../../oflog/include/dcmtk/oflog/config.h \
+ ../include/dcmtk/dcmiod/ioddef.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
  ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
@@ -411,62 +419,44 @@ iodreferences.o: iodreferences.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmiod/iodreferences.h \
- ../include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
- ../include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h
-iodrules.o: iodrules.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
  ../include/dcmtk/dcmiod/iodrules.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h
+iodrules.o: iodrules.cc ../include/dcmtk/dcmiod/iodrules.h \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../include/dcmtk/dcmiod/iodtypes.h \
+ ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/ioddef.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
@@ -479,6 +469,9 @@ iodrules.o: iodrules.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -489,34 +482,37 @@ iodrules.o: iodrules.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h
-iodtypes.o: iodtypes.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmiod/iodtypes.h \
- ../../oflog/include/dcmtk/oflog/oflog.h \
- ../../oflog/include/dcmtk/oflog/logger.h \
- ../../oflog/include/dcmtk/oflog/config.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h
+iodtypes.o: iodtypes.cc ../include/dcmtk/dcmiod/iodtypes.h \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmiod/ioddef.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
@@ -543,32 +539,41 @@ iodtypes.o: iodtypes.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/cielabutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h
-iodutil.o: iodutil.cc ../../config/include/dcmtk/config/osconfig.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
- ../../oflog/include/dcmtk/oflog/oflog.h \
- ../../oflog/include/dcmtk/oflog/logger.h \
- ../../oflog/include/dcmtk/oflog/config.h \
+iodutil.o: iodutil.cc ../include/dcmtk/dcmiod/iodutil.h \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
  ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
  ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
@@ -581,48 +586,38 @@ iodutil.o: iodutil.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/iodrules.h \
+ ../include/dcmtk/dcmiod/iodtypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcuid.h
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h
 modacquisitioncontext.o: modacquisitioncontext.cc \
- ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/modacquisitioncontext.h \
+ ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
@@ -737,27 +732,23 @@ modacquisitioncontext.o: modacquisitioncontext.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
  ../include/dcmtk/dcmiod/iodrules.h ../include/dcmtk/dcmiod/iodtypes.h \
- ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmiod/modbase.h ../include/dcmtk/dcmiod/iodutil.h \
+ ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/modbase.h \
+ ../include/dcmtk/dcmiod/iodutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
-modbase.o: modbase.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmiod/modbase.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+modbase.o: modbase.cc ../include/dcmtk/dcmiod/modbase.h \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
@@ -769,10 +760,14 @@ modbase.o: modbase.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -796,43 +791,43 @@ modbase.o: modbase.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/iodrules.h \
+ ../include/dcmtk/dcmiod/iodtypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/cielabutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
  ../include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h
+ ../../ofstd/include/dcmtk/ofstd/oftime.h
 modcommoninstanceref.o: modcommoninstanceref.cc \
- ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/modcommoninstanceref.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
- ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
- ../../ofstd/include/dcmtk/ofstd/ofcast.h \
- ../../ofstd/include/dcmtk/ofstd/ofexport.h \
- ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -922,31 +917,25 @@ modcommoninstanceref.o: modcommoninstanceref.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmiod/iodrules.h ../include/dcmtk/dcmiod/iodtypes.h \
- ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmiod/modbase.h ../include/dcmtk/dcmiod/iodmacro.h \
+ ../include/dcmtk/dcmiod/iodmacro.h ../include/dcmtk/dcmiod/iodrules.h \
+ ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/ioddef.h \
+ ../include/dcmtk/dcmiod/modbase.h \
  ../include/dcmtk/dcmiod/iodreferences.h \
  ../include/dcmtk/dcmiod/iodutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
 modenhequipment.o: modenhequipment.cc \
- ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/modenhequipment.h \
+ ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/ioddef.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../include/dcmtk/dcmiod/iodtypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
@@ -961,6 +950,9 @@ modenhequipment.o: modenhequipment.cc \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -971,7 +963,10 @@ modenhequipment.o: modenhequipment.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../include/dcmtk/dcmiod/cielabutil.h ../include/dcmtk/dcmiod/modbase.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../include/dcmtk/dcmiod/modbase.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
@@ -994,49 +989,41 @@ modenhequipment.o: modenhequipment.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
  ../include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../ofstd/include/dcmtk/ofstd/oftime.h
-modenhusimage.o: modenhusimage.cc \
+modenhusimage.o: modenhusimage.cc ../include/dcmtk/dcmiod/modenhusimage.h \
  ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmiod/modenhusimage.h \
- ../include/dcmtk/dcmiod/modbase.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
- ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
- ../../ofstd/include/dcmtk/ofstd/ofcast.h \
- ../../ofstd/include/dcmtk/ofstd/ofexport.h \
- ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -1048,36 +1035,40 @@ modenhusimage.o: modenhusimage.cc \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmiod/iodmacro.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -1122,42 +1113,38 @@ modenhusimage.o: modenhusimage.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmiod/iodrules.h ../include/dcmtk/dcmiod/iodtypes.h \
+ ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/modbase.h \
  ../include/dcmtk/dcmiod/iodutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
 modenhusseries.o: modenhusseries.cc \
- ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/modenhusseries.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../ofstd/include/dcmtk/ofstd/ofoption.h \
- ../../ofstd/include/dcmtk/ofstd/ofalign.h \
- ../include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../include/dcmtk/dcmiod/iodtypes.h \
- ../../oflog/include/dcmtk/oflog/oflog.h \
- ../../oflog/include/dcmtk/oflog/logger.h \
- ../../oflog/include/dcmtk/oflog/config.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -1168,12 +1155,10 @@ modenhusseries.o: modenhusseries.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmiod/iodmacro.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
@@ -1181,11 +1166,13 @@ modenhusseries.o: modenhusseries.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
@@ -1202,6 +1189,7 @@ modenhusseries.o: modenhusseries.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -1246,26 +1234,24 @@ modenhusseries.o: modenhusseries.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmiod/modbase.h ../include/dcmtk/dcmiod/iodutil.h \
+ ../include/dcmtk/dcmiod/iodrules.h ../include/dcmtk/dcmiod/iodtypes.h \
+ ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/modbase.h \
+ ../../ofstd/include/dcmtk/ofstd/ofoption.h \
+ ../../ofstd/include/dcmtk/ofstd/ofalign.h \
+ ../include/dcmtk/dcmiod/iodutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
-modequipment.o: modequipment.cc \
+modequipment.o: modequipment.cc ../include/dcmtk/dcmiod/modequipment.h \
  ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmiod/modequipment.h ../include/dcmtk/dcmiod/ioddef.h \
+ ../include/dcmtk/dcmiod/ioddef.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../include/dcmtk/dcmiod/iodtypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
@@ -1280,6 +1266,9 @@ modequipment.o: modequipment.cc \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -1290,7 +1279,10 @@ modequipment.o: modequipment.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../include/dcmtk/dcmiod/cielabutil.h ../include/dcmtk/dcmiod/modbase.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../include/dcmtk/dcmiod/modbase.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
@@ -1313,35 +1305,34 @@ modequipment.o: modequipment.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
  ../include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../ofstd/include/dcmtk/ofstd/oftime.h
 modfloatingpointimagepixel.o: modfloatingpointimagepixel.cc \
- ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/modfloatingpointimagepixel.h \
- ../include/dcmtk/dcmiod/modimagepixelbase.h \
- ../include/dcmtk/dcmiod/modbase.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmiod/modimagepixelbase.h \
+ ../include/dcmtk/dcmiod/modbase.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
@@ -1353,10 +1344,14 @@ modfloatingpointimagepixel.o: modfloatingpointimagepixel.cc \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -1367,7 +1362,6 @@ modfloatingpointimagepixel.o: modfloatingpointimagepixel.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
@@ -1375,41 +1369,36 @@ modfloatingpointimagepixel.o: modfloatingpointimagepixel.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/iodrules.h \
+ ../include/dcmtk/dcmiod/iodtypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
  ../include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../ofstd/include/dcmtk/ofstd/oftime.h
-modfor.o: modfor.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmiod/modfor.h ../include/dcmtk/dcmiod/modbase.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+modfor.o: modfor.cc ../include/dcmtk/dcmiod/modfor.h \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmiod/modbase.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
@@ -1421,11 +1410,15 @@ modfor.o: modfor.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
- ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
  ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
@@ -1448,40 +1441,34 @@ modfor.o: modfor.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/iodrules.h \
+ ../include/dcmtk/dcmiod/iodtypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
  ../include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../ofstd/include/dcmtk/ofstd/oftime.h
 modgeneralimage.o: modgeneralimage.cc \
- ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/modgeneralimage.h \
+ ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../include/dcmtk/dcmiod/iodtypes.h \
+ ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/ioddef.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
@@ -1494,6 +1481,9 @@ modgeneralimage.o: modgeneralimage.cc \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -1504,7 +1494,9 @@ modgeneralimage.o: modgeneralimage.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/cielabutil.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../include/dcmtk/dcmiod/modbase.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
@@ -1524,48 +1516,34 @@ modgeneralimage.o: modgeneralimage.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
- ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
  ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
  ../include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h
 modgeneralseries.o: modgeneralseries.cc \
- ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/modgeneralseries.h \
- ../include/dcmtk/dcmiod/modbase.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmiod/ioddef.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -1573,10 +1551,18 @@ modgeneralseries.o: modgeneralseries.cc \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -1588,36 +1574,40 @@ modgeneralseries.o: modgeneralseries.cc \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmiod/iodmacro.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -1662,43 +1652,37 @@ modgeneralseries.o: modgeneralseries.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmiod/iodutil.h \
+ ../include/dcmtk/dcmiod/iodrules.h ../include/dcmtk/dcmiod/iodtypes.h \
+ ../include/dcmtk/dcmiod/modbase.h ../include/dcmtk/dcmiod/iodutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
 modgeneralstudy.o: modgeneralstudy.cc \
- ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/modgeneralstudy.h \
- ../include/dcmtk/dcmiod/modbase.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
- ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
- ../../ofstd/include/dcmtk/ofstd/ofcast.h \
- ../../ofstd/include/dcmtk/ofstd/ofexport.h \
- ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -1710,36 +1694,40 @@ modgeneralstudy.o: modgeneralstudy.cc \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmiod/iodmacro.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -1784,10 +1772,12 @@ modgeneralstudy.o: modgeneralstudy.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmiod/iodrules.h ../include/dcmtk/dcmiod/iodtypes.h \
+ ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/modbase.h \
  ../include/dcmtk/dcmiod/iodutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
-modhelp.o: modhelp.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmiod/modhelp.h \
+modhelp.o: modhelp.cc ../include/dcmtk/dcmiod/modhelp.h \
+ ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
@@ -1795,9 +1785,12 @@ modhelp.o: modhelp.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oftraits.h \
@@ -1830,7 +1823,6 @@ modhelp.o: modhelp.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
@@ -1838,32 +1830,28 @@ modhelp.o: modhelp.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h
-modimagepixel.o: modimagepixel.cc \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h
+modimagepixel.o: modimagepixel.cc ../include/dcmtk/dcmiod/modimagepixel.h \
  ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmiod/modimagepixel.h \
- ../include/dcmtk/dcmiod/modimagepixelbase.h \
- ../include/dcmtk/dcmiod/modbase.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmiod/modimagepixelbase.h \
+ ../include/dcmtk/dcmiod/modbase.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
@@ -1875,10 +1863,14 @@ modimagepixel.o: modimagepixel.cc \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -1889,7 +1881,6 @@ modimagepixel.o: modimagepixel.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
@@ -1897,45 +1888,39 @@ modimagepixel.o: modimagepixel.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/iodrules.h \
+ ../include/dcmtk/dcmiod/iodtypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
  ../include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../ofstd/include/dcmtk/ofstd/oftime.h
 modimagepixelbase.o: modimagepixelbase.cc \
- ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/modimagepixelbase.h \
+ ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/modbase.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
@@ -1947,10 +1932,14 @@ modimagepixelbase.o: modimagepixelbase.cc \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -1974,40 +1963,34 @@ modimagepixelbase.o: modimagepixelbase.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/iodrules.h \
+ ../include/dcmtk/dcmiod/iodtypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/cielabutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
  ../include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../ofstd/include/dcmtk/ofstd/oftime.h
 modmultiframedimension.o: modmultiframedimension.cc \
- ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/modmultiframedimension.h \
+ ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../include/dcmtk/dcmiod/iodtypes.h \
+ ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/ioddef.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
@@ -2020,6 +2003,9 @@ modmultiframedimension.o: modmultiframedimension.cc \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -2030,7 +2016,9 @@ modmultiframedimension.o: modmultiframedimension.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/cielabutil.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../include/dcmtk/dcmiod/modbase.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
@@ -2050,24 +2038,25 @@ modmultiframedimension.o: modmultiframedimension.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpath.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpath.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../ofstd/include/dcmtk/ofstd/oftime.h
 modmultiframefg.o: modmultiframefg.cc \
- ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/modmultiframefg.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
@@ -2083,13 +2072,6 @@ modmultiframefg.o: modmultiframefg.cc \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -2115,54 +2097,60 @@ modmultiframefg.o: modmultiframefg.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/iodrules.h \
+ ../include/dcmtk/dcmiod/iodtypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/ioddef.h \
- ../include/dcmtk/dcmiod/cielabutil.h ../include/dcmtk/dcmiod/modbase.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../include/dcmtk/dcmiod/modbase.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
  ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
  ../include/dcmtk/dcmiod/iodutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
-modpatient.o: modpatient.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmiod/modpatient.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
- ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
- ../../ofstd/include/dcmtk/ofstd/ofcast.h \
- ../../ofstd/include/dcmtk/ofstd/ofexport.h \
- ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+modpatient.o: modpatient.cc ../include/dcmtk/dcmiod/modpatient.h \
+ ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -2253,38 +2241,36 @@ modpatient.o: modpatient.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
  ../include/dcmtk/dcmiod/iodrules.h ../include/dcmtk/dcmiod/iodtypes.h \
- ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmiod/modbase.h ../include/dcmtk/dcmiod/iodutil.h \
+ ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/modbase.h \
+ ../include/dcmtk/dcmiod/iodutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
 modpatientstudy.o: modpatientstudy.cc \
- ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/modpatientstudy.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
- ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
- ../../ofstd/include/dcmtk/ofstd/ofcast.h \
- ../../ofstd/include/dcmtk/ofstd/ofexport.h \
- ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofoption.h \
- ../../ofstd/include/dcmtk/ofstd/ofalign.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -2375,36 +2361,38 @@ modpatientstudy.o: modpatientstudy.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
  ../include/dcmtk/dcmiod/iodrules.h ../include/dcmtk/dcmiod/iodtypes.h \
- ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmiod/modbase.h ../include/dcmtk/dcmiod/iodutil.h \
+ ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/modbase.h \
+ ../../ofstd/include/dcmtk/ofstd/ofoption.h \
+ ../../ofstd/include/dcmtk/ofstd/ofalign.h \
+ ../include/dcmtk/dcmiod/iodutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
 modsegmentationseries.o: modsegmentationseries.cc \
- ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmiod/modsegmentationseries.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
- ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
- ../../ofstd/include/dcmtk/ofstd/ofcast.h \
- ../../ofstd/include/dcmtk/ofstd/ofexport.h \
- ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -2496,12 +2484,13 @@ modsegmentationseries.o: modsegmentationseries.cc \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
  ../include/dcmtk/dcmiod/modbase.h ../include/dcmtk/dcmiod/ioddef.h \
  ../include/dcmtk/dcmiod/iodrules.h ../include/dcmtk/dcmiod/iodtypes.h \
- ../include/dcmtk/dcmiod/cielabutil.h ../include/dcmtk/dcmiod/iodutil.h \
+ ../include/dcmtk/dcmiod/iodutil.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
-modsopcommon.o: modsopcommon.cc \
+modsopcommon.o: modsopcommon.cc ../include/dcmtk/dcmiod/modsopcommon.h \
  ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmiod/modsopcommon.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../include/dcmtk/dcmiod/modbase.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
@@ -2509,16 +2498,10 @@ modsopcommon.o: modsopcommon.cc \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../include/dcmtk/dcmiod/modbase.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
@@ -2529,10 +2512,14 @@ modsopcommon.o: modsopcommon.cc \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -2556,50 +2543,38 @@ modsopcommon.o: modsopcommon.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/iodrules.h \
+ ../include/dcmtk/dcmiod/iodtypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
  ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
  ../include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h
 modsynchronization.o: modsynchronization.cc \
  ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmiod/modsynchronisation.h \
- ../../ofstd/include/dcmtk/ofstd/ofoption.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofalign.h \
- ../include/dcmtk/dcmiod/modbase.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -2607,10 +2582,15 @@ modsynchronization.o: modsynchronization.cc \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -2621,56 +2601,57 @@ modsynchronization.o: modsynchronization.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
  ../include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/iodrules.h \
+ ../include/dcmtk/dcmiod/iodtypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h
-modusfor.o: modusfor.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmiod/modusfor.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../include/dcmtk/dcmiod/modsynchronisation.h \
+ ../include/dcmtk/dcmiod/modbase.h \
  ../../ofstd/include/dcmtk/ofstd/ofoption.h \
+ ../../ofstd/include/dcmtk/ofstd/ofalign.h
+modusfor.o: modusfor.cc ../include/dcmtk/dcmiod/modusfor.h \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmiod/modbase.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofalign.h \
- ../include/dcmtk/dcmiod/modbase.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
@@ -2682,10 +2663,14 @@ modusfor.o: modusfor.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -2709,17 +2694,19 @@ modusfor.o: modusfor.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/iodrules.h \
+ ../include/dcmtk/dcmiod/iodtypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/cielabutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../ofstd/include/dcmtk/ofstd/ofoption.h \
+ ../../ofstd/include/dcmtk/ofstd/ofalign.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
  ../include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../ofstd/include/dcmtk/ofstd/oftime.h
index fa4f315440e911372091f3e6affb4d476c70f8aa..478a92e0c2e8658b0707f6d6c3869dc0807cb564 100644 (file)
@@ -1,7 +1,6 @@
 /*
  *
- *  Copyright (C) 2005-2018, Pascal Getreuer
- *  Copyright (C) 2016, Open Connections GmbH
+ *  Copyright (C) 2005-2019, Pascal Getreuer, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -19,9 +18,9 @@
  *  Purpose: Static helper functionality for CIE<->RGB color conversions
  *
  */
-#include "dcmtk/config/osconfig.h"
 #include "dcmtk/dcmiod/cielabutil.h"
-#define INCLUDE_CMATH                // for pow() function
+#include "dcmtk/config/osconfig.h"
+#define INCLUDE_CMATH // for pow() function
 #include "dcmtk/ofstd/ofstdinc.h"
 
 // workaround for SunPro not defining these C functions in the global namespace
@@ -34,181 +33,165 @@ const double IODCIELabUtil::D65_WHITEPOINT_X = 0.950456;
 const double IODCIELabUtil::D65_WHITEPOINT_Y = 1.0;
 const double IODCIELabUtil::D65_WHITEPOINT_Z = 1.088754;
 
-
 void IODCIELabUtil::dicomLab2RGB(double& R, double& G, double& B, double LDicom, double aDicom, double bDicom)
 {
-  double L, a, b;
-  dicomlab2Lab(L, a, b, LDicom, aDicom, bDicom);
-  lab2Rgb(R, G, B, L, a, b);
+    double L, a, b;
+    dicomlab2Lab(L, a, b, LDicom, aDicom, bDicom);
+    lab2Rgb(R, G, B, L, a, b);
 }
 
-
 void IODCIELabUtil::rgb2DicomLab(double& LDicom, double& aDicom, double& bDicom, double R, double G, double B)
 {
-  double L, a, b;
-  rgb2Lab(L, a, b, R, G, B);
-  lab2DicomLab(LDicom, aDicom, bDicom, L, a, b);
+    double L, a, b;
+    rgb2Lab(L, a, b, R, G, B);
+    lab2DicomLab(LDicom, aDicom, bDicom, L, a, b);
 }
 
-
 void IODCIELabUtil::dicomlab2Lab(double& L, double& a, double& b, double LDicom, double aDicom, double bDicom)
 {
-  L = ((LDicom * 100.0) / 65535.0); // results in 0 <= L <= 100
-  a = ((aDicom * 255.0) / 65535.0) - 128; // results in -128 <= a <= 127
-  b = ((bDicom * 255.0) / 65535.0) - 128; // results in -128 <= b <= 127
+    L = ((LDicom * 100.0) / 65535.0);       // results in 0 <= L <= 100
+    a = ((aDicom * 255.0) / 65535.0) - 128; // results in -128 <= a <= 127
+    b = ((bDicom * 255.0) / 65535.0) - 128; // results in -128 <= b <= 127
 }
 
-
 void IODCIELabUtil::lab2DicomLab(double& LDicom, double& aDicom, double& bDicom, double L, double a, double b)
 {
-  LDicom = L * 65535.0 / 100.0; // results in 0 <= L <= 65535
-  aDicom = (a + 128) * 65535.0 / 255.0; // results in 0 <= a <= 65535
-  bDicom = (b + 128) * 65535.0 / 255.0; // results in 0 <= b <= 65535
+    LDicom = L * 65535.0 / 100.0;         // results in 0 <= L <= 65535
+    aDicom = (a + 128) * 65535.0 / 255.0; // results in 0 <= a <= 65535
+    bDicom = (b + 128) * 65535.0 / 255.0; // results in 0 <= b <= 65535
 }
 
-
 void IODCIELabUtil::rgb2Lab(double& L, double& a, double& b, double R, double G, double B)
 {
-  double X, Y, Z;
-  rgb2Xyz(X, Y, Z, R, G, B);
-  xyz2Lab(L, a, b, X, Y, Z);
+    double X, Y, Z;
+    rgb2Xyz(X, Y, Z, R, G, B);
+    xyz2Lab(L, a, b, X, Y, Z);
 }
 
-
 double IODCIELabUtil::gammaCorrection(double n)
 {
-  if ((n) <= 0.0031306684425005883)
-  {
-    return 12.92 * (n);
-  }
-  else
-  {
-    return (1.055*pow((n), 0.416666666666666667) - 0.055);
-  }
+    if ((n) <= 0.0031306684425005883)
+    {
+        return 12.92 * (n);
+    }
+    else
+    {
+        return (1.055 * pow((n), 0.416666666666666667) - 0.055);
+    }
 }
 
-
 double IODCIELabUtil::invGammaCorrection(double n)
 {
-  if ((n) <= 0.0404482362771076)
-  {
-    return ((n) / 12.92);
-  }
-  else
-  {
-    return ( pow(((n) + 0.055)/1.055, 2.4) );
-  }
+    if ((n) <= 0.0404482362771076)
+    {
+        return ((n) / 12.92);
+    }
+    else
+    {
+        return (pow(((n) + 0.055) / 1.055, 2.4));
+    }
 }
 
-
 void IODCIELabUtil::rgb2Xyz(double& X, double& Y, double& Z, double R, double G, double B)
 {
-  R = invGammaCorrection(R);
-  G = invGammaCorrection(G);
-  B = invGammaCorrection(B);
-  X = OFstatic_cast(double, (0.4123955889674142161*R + 0.3575834307637148171*G + 0.1804926473817015735*B));
-  Y = OFstatic_cast(double, (0.2125862307855955516*R + 0.7151703037034108499*G + 0.07220049864333622685*B));
-  Z = OFstatic_cast(double, (0.01929721549174694484*R + 0.1191838645808485318*G + 0.9504971251315797660*B));
+    R = invGammaCorrection(R);
+    G = invGammaCorrection(G);
+    B = invGammaCorrection(B);
+    X = OFstatic_cast(double, (0.4123955889674142161 * R + 0.3575834307637148171 * G + 0.1804926473817015735 * B));
+    Y = OFstatic_cast(double, (0.2125862307855955516 * R + 0.7151703037034108499 * G + 0.07220049864333622685 * B));
+    Z = OFstatic_cast(double, (0.01929721549174694484 * R + 0.1191838645808485318 * G + 0.9504971251315797660 * B));
 }
 
-
 void IODCIELabUtil::xyz2Lab(double& L, double& a, double& b, double X, double Y, double Z)
 {
-  X /= D65_WHITEPOINT_X;
-  Y /= D65_WHITEPOINT_Y;
-  Z /= D65_WHITEPOINT_Z;
-  X = labf(X);
-  Y = labf(Y);
-  Z = labf(Z);
-  L = 116*Y - 16;
-  a = 500*(X - Y);
-  b = 200*(Y - Z);
+    X /= D65_WHITEPOINT_X;
+    Y /= D65_WHITEPOINT_Y;
+    Z /= D65_WHITEPOINT_Z;
+    X = labf(X);
+    Y = labf(Y);
+    Z = labf(Z);
+    L = 116 * Y - 16;
+    a = 500 * (X - Y);
+    b = 200 * (Y - Z);
 }
 
-
 void IODCIELabUtil::lab2Rgb(double& R, double& G, double& B, double L, double a, double b)
 {
-  double  X, Y, Z;
-  lab2Xyz(X, Y, Z, L, a, b);
-  xyz2Rgb(R, G, B, X, Y, Z);
+    double X, Y, Z;
+    lab2Xyz(X, Y, Z, L, a, b);
+    xyz2Rgb(R, G, B, X, Y, Z);
 }
 
-
 void IODCIELabUtil::lab2Xyz(double& X, double& Y, double& Z, double L, double a, double b)
 {
-  L = (L + 16)/116;
-  a = L + a/500;
-  b = L - b/200;
-  X = D65_WHITEPOINT_X * labfInv(a);
-  Y = D65_WHITEPOINT_Y * labfInv(L);
-  Z = D65_WHITEPOINT_Z * labfInv(b);
+    L = (L + 16) / 116;
+    a = L + a / 500;
+    b = L - b / 200;
+    X = D65_WHITEPOINT_X * labfInv(a);
+    Y = D65_WHITEPOINT_Y * labfInv(L);
+    Z = D65_WHITEPOINT_Z * labfInv(b);
 }
 
-
 void IODCIELabUtil::xyz2Rgb(double& R, double& G, double& B, double X, double Y, double Z)
 {
-  double R1, B1, G1, Min;
+    double R1, B1, G1, Min;
 
-  R1 = OFstatic_cast(double, ( 3.2406*X - 1.5372*Y - 0.4986*Z));
-  G1 = OFstatic_cast(double, (-0.9689*X + 1.8758*Y + 0.0415*Z));
-  B1 = OFstatic_cast(double, ( 0.0557*X - 0.2040*Y + 1.0570*Z));
+    R1 = OFstatic_cast(double, (3.2406 * X - 1.5372 * Y - 0.4986 * Z));
+    G1 = OFstatic_cast(double, (-0.9689 * X + 1.8758 * Y + 0.0415 * Z));
+    B1 = OFstatic_cast(double, (0.0557 * X - 0.2040 * Y + 1.0570 * Z));
 
-  Min = min3(R1, G1, B1);
+    Min = min3(R1, G1, B1);
 
-  /* Force nonnegative values so that gamma correction is well-defined. */
-  if(Min < 0)
-  {
-    R1 -= Min;
-    G1 -= Min;
-    B1 -= Min;
-  }
+    /* Force nonnegative values so that gamma correction is well-defined. */
+    if (Min < 0)
+    {
+        R1 -= Min;
+        G1 -= Min;
+        B1 -= Min;
+    }
 
-  /* Transform from RGB to R'G'B' */
-  R = gammaCorrection(R1);
-  G = gammaCorrection(G1);
-  B = gammaCorrection(B1);
+    /* Transform from RGB to R'G'B' */
+    R = gammaCorrection(R1);
+    G = gammaCorrection(G1);
+    B = gammaCorrection(B1);
 }
 
-
 double IODCIELabUtil::labf(double n)
 {
-  if (n >= 8.85645167903563082e-3)
-  {
-    return ( pow(n, 0.333333333333333) );
-  }
-  else
-  {
-    return ( (841.0/108.0)*(n) + (4.0/29.0) );
-  }
+    if (n >= 8.85645167903563082e-3)
+    {
+        return (pow(n, 0.333333333333333));
+    }
+    else
+    {
+        return ((841.0 / 108.0) * (n) + (4.0 / 29.0));
+    }
 }
 
-
 double IODCIELabUtil::labfInv(double n)
 {
-  if ( (n) >= 0.206896551724137931 )
-  {
-    return (n)*(n)*(n);
-  }
-  else
-  {
-    return (108.0/841.0)*((n) - (4.0/29.0));
-  }
+    if ((n) >= 0.206896551724137931)
+    {
+        return (n) * (n) * (n);
+    }
+    else
+    {
+        return (108.0 / 841.0) * ((n) - (4.0 / 29.0));
+    }
 }
 
-
 double IODCIELabUtil::min2(double a, double b)
 {
-  if (a <= b)
-    return a;
-  else
-    return b;
+    if (a <= b)
+        return a;
+    else
+        return b;
 }
 
-
 double IODCIELabUtil::min3(double a, double b, double c)
 {
-  if (a <= b)
-    return min2(a,c);
-  else
-    return min2(b,c);
+    if (a <= b)
+        return min2(a, c);
+    else
+        return min2(b, c);
 }
index 06fc3112e9b00721355ed5761ed7dd251f2780cc..3c460873184b88e7b68198be221fa95c2ebe9573 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2017, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/iodcommn.h"
-#include "dcmtk/dcmdata/dctypes.h"    // logger
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+#include "dcmtk/dcmdata/dctypes.h" // logger
 #include "dcmtk/dcmiod/iodutil.h"
 
-
 DcmIODCommon::DcmIODCommon()
-: m_Item(new DcmItem()),
-  m_Rules(new IODRules),
-  m_Patient(m_Item, m_Rules),
-  m_PatientStudy(m_Item, m_Rules),
-  m_Study(m_Item, m_Rules),
-  m_Equipment(m_Item, m_Rules),
-  m_Series(m_Item, m_Rules),
-  m_FrameOfReference(m_Item, m_Rules),
-  m_SOPCommon(m_Item, m_Rules),
-  m_CommonInstanceReferenceModule(m_Item, m_Rules),
-  m_Modules()
+    : m_Item(new DcmItem())
+    , m_Rules(new IODRules)
+    , m_Patient(m_Item, m_Rules)
+    , m_PatientStudy(m_Item, m_Rules)
+    , m_Study(m_Item, m_Rules)
+    , m_Equipment(m_Item, m_Rules)
+    , m_Series(m_Item, m_Rules)
+    , m_FrameOfReference(m_Item, m_Rules)
+    , m_SOPCommon(m_Item, m_Rules)
+    , m_CommonInstanceReferenceModule(m_Item, m_Rules)
+    , m_Modules()
 {
-  // Set initial values for a new SOP instance
-  ensureInstanceUIDs(OFFalse);
-  // push this first so Specific Character Set will be written in the beginning
-  m_Modules.push_back(&m_SOPCommon);
-  m_Modules.push_back(&m_Patient);
-  m_Modules.push_back(&m_PatientStudy);
-  m_Modules.push_back(&m_Study);
-  m_Modules.push_back(&m_Equipment);
-  m_Modules.push_back(&m_Series);
-  m_Modules.push_back(&m_FrameOfReference);
-  m_Modules.push_back(&m_CommonInstanceReferenceModule);
+    // Set initial values for a new SOP instance
+    ensureInstanceUIDs(OFFalse);
+    // push this first so Specific Character Set will be written in the beginning
+    m_Modules.push_back(&m_SOPCommon);
+    m_Modules.push_back(&m_Patient);
+    m_Modules.push_back(&m_PatientStudy);
+    m_Modules.push_back(&m_Study);
+    m_Modules.push_back(&m_Equipment);
+    m_Modules.push_back(&m_Series);
+    m_Modules.push_back(&m_FrameOfReference);
+    m_Modules.push_back(&m_CommonInstanceReferenceModule);
 }
 
-
 DcmIODCommon::DcmIODCommon(const DcmIODCommon& rhs)
-: m_Item(rhs.m_Item),
-  m_Rules(rhs.m_Rules),
-  m_Patient(m_Item, m_Rules),
-  m_PatientStudy(m_Item, m_Rules),
-  m_Study(m_Item, m_Rules),
-  m_Equipment(m_Item, m_Rules),
-  m_Series(m_Item, m_Rules),
-  m_FrameOfReference(m_Item, m_Rules),
-  m_SOPCommon(m_Item, m_Rules),
-  m_CommonInstanceReferenceModule(m_Item, m_Rules),
-  m_Modules()
+    : m_Item(rhs.m_Item)
+    , m_Rules(rhs.m_Rules)
+    , m_Patient(m_Item, m_Rules)
+    , m_PatientStudy(m_Item, m_Rules)
+    , m_Study(m_Item, m_Rules)
+    , m_Equipment(m_Item, m_Rules)
+    , m_Series(m_Item, m_Rules)
+    , m_FrameOfReference(m_Item, m_Rules)
+    , m_SOPCommon(m_Item, m_Rules)
+    , m_CommonInstanceReferenceModule(m_Item, m_Rules)
+    , m_Modules()
 {
-  // Set initial values for a new SOP instance
-  ensureInstanceUIDs(OFFalse);
-  // push this first so Specific Character Set will be written in the beginning
-  m_Modules.push_back(&m_SOPCommon);
-  m_Modules.push_back(&m_Patient);
-  m_Modules.push_back(&m_PatientStudy);
-  m_Modules.push_back(&m_Study);
-  m_Modules.push_back(&m_Equipment);
-  m_Modules.push_back(&m_Series);
-  m_Modules.push_back(&m_FrameOfReference);
-  m_Modules.push_back(&m_CommonInstanceReferenceModule);
+    // Set initial values for a new SOP instance
+    ensureInstanceUIDs(OFFalse);
+    // push this first so Specific Character Set will be written in the beginning
+    m_Modules.push_back(&m_SOPCommon);
+    m_Modules.push_back(&m_Patient);
+    m_Modules.push_back(&m_PatientStudy);
+    m_Modules.push_back(&m_Study);
+    m_Modules.push_back(&m_Equipment);
+    m_Modules.push_back(&m_Series);
+    m_Modules.push_back(&m_FrameOfReference);
+    m_Modules.push_back(&m_CommonInstanceReferenceModule);
 }
 
-
 DcmIODCommon::~DcmIODCommon()
 {
 }
 
-
 void DcmIODCommon::clearData()
 {
-  // TODO
-//   OFVector<IODModule*>::iterator it = m_Modules.begin();
-//   while (it != m_Modules.end())
-//   {
-//     (*it)->clearData();
-//     it++;
-//   }
+    // TODO
+    //   OFVector<IODModule*>::iterator it = m_Modules.begin();
+    //   while (it != m_Modules.end())
+    //   {
+    //     (*it)->clearData();
+    //     it++;
+    //   }
 }
 
-
 IODPatientModule& DcmIODCommon::getPatient()
 {
-  return m_Patient;
+    return m_Patient;
 }
 
-
 IODPatientStudyModule& DcmIODCommon::getPatientStudy()
 {
-  return m_PatientStudy;
+    return m_PatientStudy;
 }
 
-
 IODGeneralStudyModule& DcmIODCommon::getStudy()
 {
-  return m_Study;
+    return m_Study;
 }
 
-
 IODGeneralEquipmentModule& DcmIODCommon::getEquipment()
 {
-  return m_Equipment;
+    return m_Equipment;
 }
 
-
 IODGeneralSeriesModule& DcmIODCommon::getSeries()
 {
-  return m_Series;
+    return m_Series;
 }
 
-
 IODFoRModule& DcmIODCommon::getFrameOfReference()
 {
-  return m_FrameOfReference;
+    return m_FrameOfReference;
 }
 
-
 IODSOPCommonModule& DcmIODCommon::getSOPCommon()
 {
-  return m_SOPCommon;
+    return m_SOPCommon;
 }
 
-
 IODCommonInstanceReferenceModule& DcmIODCommon::getCommonInstanceReference()
 {
-  return m_CommonInstanceReferenceModule;
+    return m_CommonInstanceReferenceModule;
 }
 
-
-
 OFshared_ptr<IODRules> DcmIODCommon::getRules()
 {
-  return m_Rules;
+    return m_Rules;
 }
 
-
 OFshared_ptr<DcmItem> DcmIODCommon::getData()
 {
-  return m_Item;
+    return m_Item;
 }
 
-
-OFCondition DcmIODCommon::read(DcmItem &dataset)
+OFCondition DcmIODCommon::read(DcmItem& dataset)
 {
-  /* re-initialize object */
-  DcmIODCommon::clearData();
-
-  OFVector<IODModule*>::iterator it = m_Modules.begin();
-  while ( it != m_Modules.end() )
-  {
-    (*it)->read(dataset, OFTrue /* clear old data */);
-    it++;
-  }
-
-  // we do not report errors here (only logger output)
-  return EC_Normal;
-}
+    /* re-initialize object */
+    DcmIODCommon::clearData();
 
+    OFVector<IODModule*>::iterator it = m_Modules.begin();
+    while (it != m_Modules.end())
+    {
+        (*it)->read(dataset, OFTrue /* clear old data */);
+        it++;
+    }
+
+    // we do not report errors here (only logger output)
+    return EC_Normal;
+}
 
 OFCondition DcmIODCommon::importHierarchy(DcmItem& dataset,
                                           const OFBool readPatient,
@@ -181,53 +164,52 @@ OFCondition DcmIODCommon::importHierarchy(DcmItem& dataset,
                                           const OFBool readSeries,
                                           const OFBool takeOverCharset)
 {
-  if (readPatient)
-  {
-    m_Patient.read(dataset, OFFalse /* do not clear old data */);
-  }
-
-  if (readStudy)
-  {
-    m_Study.read(dataset, OFFalse /* do not clear old data */);
-    m_Equipment.read(dataset, OFFalse /* do not clear old data */);
-    m_PatientStudy.read(dataset, OFFalse /* do not clear old data */);
-  }
-
-  if (readSeries)
-  {
-    m_Series.read(dataset, OFFalse /* do not clear old data */);
-    m_FrameOfReference.read(dataset, OFFalse /* do not clear old data */);
-  }
-
-  if (readFoR)
-  {
-    m_FrameOfReference.read(dataset, OFFalse /* do not clear old data */);
-  }
-
-  // Take over character set from the dataset imported, if desired
-  if (takeOverCharset)
-  {
-    OFString charset;
-    dataset.findAndGetOFStringArray(DCM_SpecificCharacterSet, charset);
-    if (!charset.empty())
+    if (readPatient)
+    {
+        m_Patient.read(dataset, OFFalse /* do not clear old data */);
+    }
+
+    if (readStudy)
     {
-      DCMIOD_DEBUG("Taking over Specific Character Set " << charset << " on import");
-      OFCondition result = m_SOPCommon.setSpecificCharacterSet(charset);
-      if (result.bad())
-      {
-        DCMIOD_ERROR("Could not set Specific Character Set " << charset << " on import: " << result.text());
-      }
+        m_Study.read(dataset, OFFalse /* do not clear old data */);
+        m_Equipment.read(dataset, OFFalse /* do not clear old data */);
+        m_PatientStudy.read(dataset, OFFalse /* do not clear old data */);
     }
-    else
+
+    if (readSeries)
     {
-        DCMIOD_DEBUG("Taking over Default Specific Character Set (ASCII) on import");
-        m_SOPCommon.getData().findAndDeleteElement(DCM_SpecificCharacterSet);
+        m_Series.read(dataset, OFFalse /* do not clear old data */);
+        m_FrameOfReference.read(dataset, OFFalse /* do not clear old data */);
     }
-  }
 
-  return EC_Normal;
-}
+    if (readFoR)
+    {
+        m_FrameOfReference.read(dataset, OFFalse /* do not clear old data */);
+    }
 
+    // Take over character set from the dataset imported, if desired
+    if (takeOverCharset)
+    {
+        OFString charset;
+        dataset.findAndGetOFStringArray(DCM_SpecificCharacterSet, charset);
+        if (!charset.empty())
+        {
+            DCMIOD_DEBUG("Taking over Specific Character Set " << charset << " on import");
+            OFCondition result = m_SOPCommon.setSpecificCharacterSet(charset);
+            if (result.bad())
+            {
+                DCMIOD_ERROR("Could not set Specific Character Set " << charset << " on import: " << result.text());
+            }
+        }
+        else
+        {
+            DCMIOD_DEBUG("Taking over Default Specific Character Set (ASCII) on import");
+            m_SOPCommon.getData().findAndDeleteElement(DCM_SpecificCharacterSet);
+        }
+    }
+
+    return EC_Normal;
+}
 
 OFCondition DcmIODCommon::importHierarchy(const OFString& filename,
                                           const OFBool readPatient,
@@ -236,82 +218,76 @@ OFCondition DcmIODCommon::importHierarchy(const OFString& filename,
                                           const OFBool readSeries,
                                           const OFBool takeOverCharset)
 {
-  DcmFileFormat dcmff;
-  OFCondition result = dcmff.loadFile(filename.c_str());
-  if ( result.good() )
-  {
-    DcmDataset *dset = dcmff.getDataset();
-    if (dset != NULL)
-    {
-      result = importHierarchy(*dset, readPatient, readStudy, readFoR, readSeries, takeOverCharset);
-    }
-    else
+    DcmFileFormat dcmff;
+    OFCondition result = dcmff.loadFile(filename.c_str());
+    if (result.good())
     {
-      DCMIOD_ERROR("Unable to get dataset from file for copying patient, study, series and/or frame of reference information");
-      result = EC_IllegalCall;
+        DcmDataset* dset = dcmff.getDataset();
+        if (dset != NULL)
+        {
+            result = importHierarchy(*dset, readPatient, readStudy, readFoR, readSeries, takeOverCharset);
+        }
+        else
+        {
+            DCMIOD_ERROR("Unable to get dataset from file for copying patient, study, series and/or frame of reference "
+                         "information");
+            result = EC_IllegalCall;
+        }
     }
-  }
-  return result;
+    return result;
 }
 
-
 void DcmIODCommon::ensureInstanceUIDs(const OFBool correctInvalid)
 {
-  m_Study.ensureInstanceUID(correctInvalid);
-  m_Series.ensureInstanceUID(correctInvalid);
-  m_SOPCommon.ensureInstanceUID(correctInvalid);
+    m_Study.ensureInstanceUID(correctInvalid);
+    m_Series.ensureInstanceUID(correctInvalid);
+    m_SOPCommon.ensureInstanceUID(correctInvalid);
 }
 
-
-OFCondition DcmIODCommon::write(DcmItem &dataset)
+OFCondition DcmIODCommon::write(DcmItem& dataset)
 {
-  OFCondition result;
-
-  OFVector<IODModule*>::iterator it = m_Modules.begin();
-  while ( (it != m_Modules.end() && result.good()) )
-  {
-    result = (*it)->write(dataset);
-    it++;
-  }
-  return result;
-}
+    OFCondition result;
 
+    OFVector<IODModule*>::iterator it = m_Modules.begin();
+    while ((it != m_Modules.end() && result.good()))
+    {
+        result = (*it)->write(dataset);
+        it++;
+    }
+    return result;
+}
 
 void DcmIODCommon::createNewStudy(const OFBool clearEquipment)
 {
-  // clear all study-related attributes
-  m_Study.clearData();
-  m_PatientStudy.clearData();
-  if (clearEquipment)
-    m_Equipment.clearData();
-  // make sure we have a valid Study Instance UID
-  m_Study.ensureInstanceUID();
-
-  // reset series- and instance related attributes
-  createNewSeries();
+    // clear all study-related attributes
+    m_Study.clearData();
+    m_PatientStudy.clearData();
+    if (clearEquipment)
+        m_Equipment.clearData();
+    // make sure we have a valid Study Instance UID
+    m_Study.ensureInstanceUID();
+
+    // reset series- and instance related attributes
+    createNewSeries();
 }
 
-
 void DcmIODCommon::createNewSeries(const OFBool clearFoR)
 {
-  // clear all series-related attributes
-  m_Series.clearData();
-  // create new Series Instance UID
-  m_Series.ensureInstanceUID();
+    // clear all series-related attributes
+    m_Series.clearData();
+    // create new Series Instance UID
+    m_Series.ensureInstanceUID();
 
-  // clear frame of reference-related attributes if desired
-  if (clearFoR)
-    m_FrameOfReference.clearData();
+    // clear frame of reference-related attributes if desired
+    if (clearFoR)
+        m_FrameOfReference.clearData();
 
-  /* also creates new series (since UID is empty) */
-  createNewSOPInstance();
+    /* also creates new series (since UID is empty) */
+    createNewSOPInstance();
 }
 
-
 void DcmIODCommon::createNewSOPInstance()
 {
-  m_SOPCommon.clearData();
-  m_SOPCommon.ensureInstanceUID();
+    m_SOPCommon.clearData();
+    m_SOPCommon.ensureInstanceUID();
 }
-
-
index a96793cb03aff926b3e187f94d2bdb05ae6dd7dc..4858e06a8ed0b47f3c15b51e4a202560dc26003b 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016-2018, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  */
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/ofstd/ofstream.h"
 #include "dcmtk/dcmdata/dcdeftag.h"
 #include "dcmtk/dcmdata/dcvrcs.h"
-#include "dcmtk/dcmdata/dcvrdt.h"
 #include "dcmtk/dcmdata/dcvrda.h"
+#include "dcmtk/dcmdata/dcvrdt.h"
 #include "dcmtk/dcmdata/dcvrtm.h"
+#include "dcmtk/ofstd/ofstream.h"
 
-#include "dcmtk/dcmiod/iodutil.h"
 #include "dcmtk/dcmiod/iodcontentitemmacro.h"
+#include "dcmtk/dcmiod/iodutil.h"
 
 const OFString ContentItemMacro::ReferencedSOPSequenceItem::m_ComponentName = "ReferencedSOPSequenceItem";
 
-
 ContentItemMacro::ReferencedSOPSequenceItem::ReferencedSOPSequenceItem(OFshared_ptr<DcmItem> item,
-                                                     OFshared_ptr<IODRules> rules,
-                                                     IODComponent* parent)
-: IODComponent(item, rules, parent),
-  m_SOPInstanceReferenceMacro()
+                                                                       OFshared_ptr<IODRules> rules,
+                                                                       IODComponent* parent)
+    : IODComponent(item, rules, parent)
+    , m_SOPInstanceReferenceMacro()
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 ContentItemMacro::ReferencedSOPSequenceItem::ReferencedSOPSequenceItem(IODComponent* parent)
-: IODComponent(parent),
-  m_SOPInstanceReferenceMacro()
+    : IODComponent(parent)
+    , m_SOPInstanceReferenceMacro()
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 ContentItemMacro::ReferencedSOPSequenceItem::ReferencedSOPSequenceItem(const ReferencedSOPSequenceItem& rhs)
-: IODComponent(rhs),
-  m_SOPInstanceReferenceMacro()
+    : IODComponent(rhs)
+    , m_SOPInstanceReferenceMacro()
 {
 }
 
-
 ContentItemMacro::ReferencedSOPSequenceItem::~ReferencedSOPSequenceItem()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
 OFString ContentItemMacro::ReferencedSOPSequenceItem::getName() const
 {
-  return m_ComponentName;
+    return m_ComponentName;
 }
 
-
 void ContentItemMacro::ReferencedSOPSequenceItem::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_ReferencedFrameNumber, "1-n","1C", getName(), DcmIODTypes::IE_UNDEFINED), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ReferencedSegmentNumber, "1-n","1C", getName(), DcmIODTypes::IE_UNDEFINED), OFTrue);
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_ReferencedFrameNumber, "1-n", "1C", getName(), DcmIODTypes::IE_UNDEFINED), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ReferencedSegmentNumber, "1-n", "1C", getName(), DcmIODTypes::IE_UNDEFINED),
+                     OFTrue);
 }
 
-
-OFCondition ContentItemMacro::ReferencedSOPSequenceItem::read(
-  DcmItem& source,
-  const OFBool clearOldData)
+OFCondition ContentItemMacro::ReferencedSOPSequenceItem::read(DcmItem& source, const OFBool clearOldData)
 {
-  if (clearOldData)
-    clearData();
+    if (clearOldData)
+        clearData();
 
-  IODComponent::read(source, OFFalse /* data already cleared */);
-  return EC_Normal;
+    IODComponent::read(source, OFFalse /* data already cleared */);
+    return EC_Normal;
 }
 
-
 OFCondition ContentItemMacro::ReferencedSOPSequenceItem::write(DcmItem& destination)
 {
-  OFCondition result = EC_Normal;
+    OFCondition result = EC_Normal;
 
-  result = IODComponent::write(destination);
+    result = IODComponent::write(destination);
 
-  return result;
+    return result;
 }
 
-
 SOPInstanceReferenceMacro& ContentItemMacro::ReferencedSOPSequenceItem::getSOPInstanceReferenceMacro()
 {
-  return m_SOPInstanceReferenceMacro;
+    return m_SOPInstanceReferenceMacro;
 }
 
-
-OFCondition ContentItemMacro::ReferencedSOPSequenceItem::getReferencedFrameNumber(
-  OFString &value,
-  const signed long pos) const
+OFCondition ContentItemMacro::ReferencedSOPSequenceItem::getReferencedFrameNumber(OFString& value,
+                                                                                  const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_ReferencedFrameNumber, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_ReferencedFrameNumber, *m_Item, value, pos);
 }
 
-
-OFCondition ContentItemMacro::ReferencedSOPSequenceItem::getReferencedSegmentNumber(
-  Uint16 &value,
-  const signed long pos) const
+OFCondition ContentItemMacro::ReferencedSOPSequenceItem::getReferencedSegmentNumber(Uint16& value,
+                                                                                    const unsigned long pos) const
 {
-  return m_Item->findAndGetUint16(DCM_ReferencedSegmentNumber, value, pos);
+    return m_Item->findAndGetUint16(DCM_ReferencedSegmentNumber, value, pos);
 }
 
-
-OFCondition ContentItemMacro::ReferencedSOPSequenceItem::setReferencedFrameNumber(
-  const OFString &value,
-  const OFBool checkValue)
+OFCondition ContentItemMacro::ReferencedSOPSequenceItem::setReferencedFrameNumber(const OFString& value,
+                                                                                  const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmIntegerString::checkStringValue(value, "1-n") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_ReferencedFrameNumber, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmIntegerString::checkStringValue(value, "1-n") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_ReferencedFrameNumber, value);
+    return result;
 }
 
-
-OFCondition ContentItemMacro::ReferencedSOPSequenceItem::setReferencedSegmentNumber(
-  const Uint16 value,
-  const OFBool checkValue)
+OFCondition ContentItemMacro::ReferencedSOPSequenceItem::setReferencedSegmentNumber(const Uint16 value,
+                                                                                    const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertUint16(DCM_ReferencedSegmentNumber, value);
+    (void)checkValue;
+    return m_Item->putAndInsertUint16(DCM_ReferencedSegmentNumber, value);
 }
 
-
 const OFString ContentItemMacro::m_ModuleName = "ContentItemMacro";
 
-
 ContentItemMacro::ContentItemMacro()
-: IODComponent(),
-  m_ConceptNameCodeSequence(),
-  m_ConceptCodeSequence(),
-  m_MeasurementUnitsCodeSequence(),
-  m_ReferencedSOPSequence()
+    : IODComponent()
+    , m_ConceptNameCodeSequence()
+    , m_ConceptCodeSequence()
+    , m_MeasurementUnitsCodeSequence()
+    , m_ReferencedSOPSequence()
 {
-  resetRules();
+    resetRules();
 }
 
-
-ContentItemMacro::ContentItemMacro(OFshared_ptr<DcmItem> item,
-                                   OFshared_ptr<IODRules> rules)
-: IODComponent(item, rules),
-  m_ConceptNameCodeSequence(),
-  m_ConceptCodeSequence(),
-  m_MeasurementUnitsCodeSequence(),
-  m_ReferencedSOPSequence()
+ContentItemMacro::ContentItemMacro(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODComponent(item, rules)
+    , m_ConceptNameCodeSequence()
+    , m_ConceptCodeSequence()
+    , m_MeasurementUnitsCodeSequence()
+    , m_ReferencedSOPSequence()
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 ContentItemMacro::ContentItemMacro(const ContentItemMacro& rhs)
-: IODComponent(rhs),
-  m_ConceptNameCodeSequence(),
-  m_ConceptCodeSequence(),
-  m_MeasurementUnitsCodeSequence(),
-  m_ReferencedSOPSequence()
-{
-  if (this == &rhs)
-    return;
-
-  OFVector<CodeSequenceMacro*>::const_iterator it = rhs.m_ConceptCodeSequence.begin();
-  while (it != rhs.m_ConceptCodeSequence.end())
-  {
-    CodeSequenceMacro* macro = new CodeSequenceMacro(**it);
-    m_ConceptCodeSequence.push_back(macro);
-    it++;
-  }
-
-  it = rhs.m_ConceptNameCodeSequence.begin();
-  while (it != rhs.m_ConceptNameCodeSequence.end())
-  {
-    CodeSequenceMacro* macro = new CodeSequenceMacro(**it);
-    m_ConceptNameCodeSequence.push_back(macro);
-    it++;
-  }
-
-  it = rhs.m_MeasurementUnitsCodeSequence.begin();
-  while (it != rhs.m_MeasurementUnitsCodeSequence.end())
-  {
-    CodeSequenceMacro* macro = new CodeSequenceMacro(**it);
-    m_MeasurementUnitsCodeSequence.push_back(macro);
-    it++;
-  }
-
-  OFVector<ReferencedSOPSequenceItem*>::const_iterator m = rhs.m_ReferencedSOPSequence.begin();
-  while (m != rhs.m_ReferencedSOPSequence.end())
-  {
-    ReferencedSOPSequenceItem* item = new ReferencedSOPSequenceItem(**m);
-    m_ReferencedSOPSequence.push_back(item);
-    m++;
-  }
+    : IODComponent(rhs)
+    , m_ConceptNameCodeSequence()
+    , m_ConceptCodeSequence()
+    , m_MeasurementUnitsCodeSequence()
+    , m_ReferencedSOPSequence()
+{
+    if (this == &rhs)
+        return;
 
-}
+    OFVector<CodeSequenceMacro*>::const_iterator it = rhs.m_ConceptCodeSequence.begin();
+    while (it != rhs.m_ConceptCodeSequence.end())
+    {
+        CodeSequenceMacro* macro = new CodeSequenceMacro(**it);
+        m_ConceptCodeSequence.push_back(macro);
+        it++;
+    }
+
+    it = rhs.m_ConceptNameCodeSequence.begin();
+    while (it != rhs.m_ConceptNameCodeSequence.end())
+    {
+        CodeSequenceMacro* macro = new CodeSequenceMacro(**it);
+        m_ConceptNameCodeSequence.push_back(macro);
+        it++;
+    }
+
+    it = rhs.m_MeasurementUnitsCodeSequence.begin();
+    while (it != rhs.m_MeasurementUnitsCodeSequence.end())
+    {
+        CodeSequenceMacro* macro = new CodeSequenceMacro(**it);
+        m_MeasurementUnitsCodeSequence.push_back(macro);
+        it++;
+    }
 
+    OFVector<ReferencedSOPSequenceItem*>::const_iterator m = rhs.m_ReferencedSOPSequence.begin();
+    while (m != rhs.m_ReferencedSOPSequence.end())
+    {
+        ReferencedSOPSequenceItem* item = new ReferencedSOPSequenceItem(**m);
+        m_ReferencedSOPSequence.push_back(item);
+        m++;
+    }
+}
 
 ContentItemMacro::~ContentItemMacro()
 {
-  DcmIODUtil::freeContainer(m_ConceptNameCodeSequence);
-  DcmIODUtil::freeContainer(m_ConceptCodeSequence);
-  DcmIODUtil::freeContainer(m_MeasurementUnitsCodeSequence);
-  DcmIODUtil::freeContainer(m_ReferencedSOPSequence);
+    DcmIODUtil::freeContainer(m_ConceptNameCodeSequence);
+    DcmIODUtil::freeContainer(m_ConceptCodeSequence);
+    DcmIODUtil::freeContainer(m_MeasurementUnitsCodeSequence);
+    DcmIODUtil::freeContainer(m_ReferencedSOPSequence);
 }
 
-
 OFString ContentItemMacro::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 void ContentItemMacro::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_ValueType, "1","1", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ConceptNameCodeSequence, "1","1", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_DateTime, "1","1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_Date, "1","1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_Time, "1","1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PersonName, "1","1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_UID, "1","1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_TextValue, "1","1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ConceptCodeSequence, "1","1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_NumericValue, "1-n","1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_FloatingPointValue, "1-n","1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_RationalNumeratorValue, "1-n","1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_RationalDenominatorValue, "1-n","1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_MeasurementUnitsCodeSequence, "1","1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ReferencedSOPSequence, "1","1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-}
-
-
-OFCondition ContentItemMacro::read(DcmItem& source,
-                                   const OFBool clearOldData)
-{
-  if (clearOldData)
-    clearData();
-
-  IODComponent::read(source, OFFalse /* data already cleared */);
-  DcmIODUtil::readSubSequence(source, DCM_ConceptNameCodeSequence, m_ConceptNameCodeSequence, m_Rules->getByTag(DCM_ConceptNameCodeSequence));
-  DcmIODUtil::readSubSequence(source, DCM_ConceptCodeSequence, m_ConceptCodeSequence, m_Rules->getByTag(DCM_ConceptCodeSequence));
-  DcmIODUtil::readSubSequence(source, DCM_MeasurementUnitsCodeSequence, m_MeasurementUnitsCodeSequence, m_Rules->getByTag(DCM_MeasurementUnitsCodeSequence));
-  DcmIODUtil::readSubSequence(source, DCM_ReferencedSOPSequence, m_ReferencedSOPSequence, m_Rules->getByTag(DCM_ReferencedSOPSequence));
-
-  return EC_Normal;
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_ValueType, "1", "1", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ConceptNameCodeSequence, "1", "1", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_DateTime, "1", "1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_Date, "1", "1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_Time, "1", "1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PersonName, "1", "1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_UID, "1", "1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_TextValue, "1", "1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ConceptCodeSequence, "1", "1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_NumericValue, "1-n", "1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_FloatingPointValue, "1-n", "1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_RationalNumeratorValue, "1-n", "1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_RationalDenominatorValue, "1-n", "1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_MeasurementUnitsCodeSequence, "1", "1C", getName(), DcmIODTypes::IE_SERIES),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ReferencedSOPSequence, "1", "1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+}
+
+OFCondition ContentItemMacro::read(DcmItem& source, const OFBool clearOldData)
+{
+    if (clearOldData)
+        clearData();
+
+    IODComponent::read(source, OFFalse /* data already cleared */);
+    DcmIODUtil::readSubSequence(
+        source, DCM_ConceptNameCodeSequence, m_ConceptNameCodeSequence, m_Rules->getByTag(DCM_ConceptNameCodeSequence));
+    DcmIODUtil::readSubSequence(
+        source, DCM_ConceptCodeSequence, m_ConceptCodeSequence, m_Rules->getByTag(DCM_ConceptCodeSequence));
+    DcmIODUtil::readSubSequence(source,
+                                DCM_MeasurementUnitsCodeSequence,
+                                m_MeasurementUnitsCodeSequence,
+                                m_Rules->getByTag(DCM_MeasurementUnitsCodeSequence));
+    DcmIODUtil::readSubSequence(
+        source, DCM_ReferencedSOPSequence, m_ReferencedSOPSequence, m_Rules->getByTag(DCM_ReferencedSOPSequence));
+
+    return EC_Normal;
 }
 
-
 OFCondition ContentItemMacro::write(DcmItem& destination)
 {
-  OFCondition result = EC_Normal;
-
-  if(CodeSequenceMacro* pConceptNameCodeSequence = getConceptNameCodeSequence())
-    DcmIODUtil::writeSingleItem(result, DCM_ConceptNameCodeSequence, *pConceptNameCodeSequence, *m_Item, m_Rules->getByTag(DCM_ConceptNameCodeSequence));
-  if(CodeSequenceMacro* pConceptCodeSequence = getConceptCodeSequence())
-    DcmIODUtil::writeSingleItem(result, DCM_ConceptCodeSequence, *pConceptCodeSequence, *m_Item, m_Rules->getByTag(DCM_ConceptCodeSequence));
-  if(CodeSequenceMacro* pMeasurementUnitsCodeSequence = getMeasurementUnitsCodeSequence())
-    DcmIODUtil::writeSingleItem(result, DCM_MeasurementUnitsCodeSequence, *pMeasurementUnitsCodeSequence, *m_Item, m_Rules->getByTag(DCM_MeasurementUnitsCodeSequence));
-  if(ReferencedSOPSequenceItem* pReferencedSOPSequence = getReferencedSOPSequence())
-    DcmIODUtil::writeSingleItem(result, DCM_ReferencedSOPSequence, *pReferencedSOPSequence, *m_Item, m_Rules->getByTag(DCM_ReferencedSOPSequence));
-
-  if (result.good())
-  {
-    result = IODComponent::write(destination);
-  }
+    OFCondition result = EC_Normal;
+
+    if (CodeSequenceMacro* pConceptNameCodeSequence = getConceptNameCodeSequence())
+        DcmIODUtil::writeSingleItem(result,
+                                    DCM_ConceptNameCodeSequence,
+                                    *pConceptNameCodeSequence,
+                                    *m_Item,
+                                    m_Rules->getByTag(DCM_ConceptNameCodeSequence));
+    if (CodeSequenceMacro* pConceptCodeSequence = getConceptCodeSequence())
+        DcmIODUtil::writeSingleItem(result,
+                                    DCM_ConceptCodeSequence,
+                                    *pConceptCodeSequence,
+                                    *m_Item,
+                                    m_Rules->getByTag(DCM_ConceptCodeSequence));
+    if (CodeSequenceMacro* pMeasurementUnitsCodeSequence = getMeasurementUnitsCodeSequence())
+        DcmIODUtil::writeSingleItem(result,
+                                    DCM_MeasurementUnitsCodeSequence,
+                                    *pMeasurementUnitsCodeSequence,
+                                    *m_Item,
+                                    m_Rules->getByTag(DCM_MeasurementUnitsCodeSequence));
+    if (ReferencedSOPSequenceItem* pReferencedSOPSequence = getReferencedSOPSequence())
+        DcmIODUtil::writeSingleItem(result,
+                                    DCM_ReferencedSOPSequence,
+                                    *pReferencedSOPSequence,
+                                    *m_Item,
+                                    m_Rules->getByTag(DCM_ReferencedSOPSequence));
+
+    if (result.good())
+    {
+        result = IODComponent::write(destination);
+    }
 
-  return result;
+    return result;
 }
 
-
-OFCondition ContentItemMacro::getValueType(OFString &value,
-                                           const signed long pos) const
+OFCondition ContentItemMacro::getValueType(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_ValueType, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_ValueType, *m_Item, value, pos);
 }
 
-
 OFCondition ContentItemMacro::getValueType(ValueType& value) const
 {
-  OFString str;
-  OFCondition result = DcmIODUtil::getStringValueFromItem(DCM_ValueType, *m_Item, str, 0);
-  if (result == EC_Normal)
-  {
-    if (!str.empty())
+    OFString str;
+    OFCondition result = DcmIODUtil::getStringValueFromItem(DCM_ValueType, *m_Item, str, 0);
+    if (result == EC_Normal)
     {
-      if (str == "DATE")
-        value = VT_DATE;
-      else if (str == "TIME")
-        value = VT_TIME;
-      else if (str == "DATETIME")
-        value = VT_DATETIME;
-      else if (str == "PNAME")
-        value = VT_PNAME;
-      else if (str == "UIDREF")
-        value = VT_UIDREF;
-      else if (str == "TEXT")
-        value = VT_TEXT;
-      else if (str == "CODE")
-        value = VT_CODE;
-      else if (str == "NUMERIC")
-        value = VT_NUMERIC;
-      else if (str == "COMPOSITE")
-        value = VT_COMPOSITE;
-      else if (str == "IMAGE")
-        value = VT_IMAGE;
-      else
-        value = VT_UNKNOWN;
+        if (!str.empty())
+        {
+            if (str == "DATE")
+                value = VT_DATE;
+            else if (str == "TIME")
+                value = VT_TIME;
+            else if (str == "DATETIME")
+                value = VT_DATETIME;
+            else if (str == "PNAME")
+                value = VT_PNAME;
+            else if (str == "UIDREF")
+                value = VT_UIDREF;
+            else if (str == "TEXT")
+                value = VT_TEXT;
+            else if (str == "CODE")
+                value = VT_CODE;
+            else if (str == "NUMERIC")
+                value = VT_NUMERIC;
+            else if (str == "COMPOSITE")
+                value = VT_COMPOSITE;
+            else if (str == "IMAGE")
+                value = VT_IMAGE;
+            else
+                value = VT_UNKNOWN;
+        }
+        else
+        {
+            value = VT_EMPTY;
+        }
+    }
+    else if (result == EC_TagNotFound)
+    {
+        value = VT_EMPTY;
     }
     else
     {
-      value = VT_EMPTY;
+        DCMIOD_ERROR("Unexpected error, could not get Value Type: " << result.text());
+        value = VT_UNKNOWN;
     }
-  }
-  else if (result == EC_TagNotFound)
-  {
-    value = VT_EMPTY;
-  }
-  else
-  {
-    DCMIOD_ERROR("Unexpected error, could not get Value Type: " << result.text());
-    value = VT_UNKNOWN;
-  }
-  return result;
+    return result;
 }
 
-
 CodeSequenceMacro* ContentItemMacro::getConceptNameCodeSequence()
 {
-  return m_ConceptNameCodeSequence.empty() ? OFnullptr : *m_ConceptNameCodeSequence.begin();
+    return m_ConceptNameCodeSequence.empty() ? OFnullptr : *m_ConceptNameCodeSequence.begin();
 }
 
 OFVector<CodeSequenceMacro*>& ContentItemMacro::getEntireConceptNameCodeSequence()
 {
-  return m_ConceptNameCodeSequence;
+    return m_ConceptNameCodeSequence;
 }
 
-
-OFCondition ContentItemMacro::getDateTime(OFString &value,
-                                          const signed long pos) const
+OFCondition ContentItemMacro::getDateTime(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_DateTime, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_DateTime, *m_Item, value, pos);
 }
 
-
-OFCondition ContentItemMacro::getDate(OFString &value,
-                                      const signed long pos) const
+OFCondition ContentItemMacro::getDate(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_Date, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_Date, *m_Item, value, pos);
 }
 
-
-OFCondition ContentItemMacro::getTime(OFString &value,
-                                      const signed long pos) const
+OFCondition ContentItemMacro::getTime(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_Time, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_Time, *m_Item, value, pos);
 }
 
-
-OFCondition ContentItemMacro::getPersonName(OFString &value,
-                                            const signed long pos) const
+OFCondition ContentItemMacro::getPersonName(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_PersonName, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_PersonName, *m_Item, value, pos);
 }
 
-
-OFCondition ContentItemMacro::getUID(OFString &value,
-                                     const signed long pos) const
+OFCondition ContentItemMacro::getUID(OFString& value, const signed long pos) const
 {
-  return m_Item->findAndGetOFString(DCM_UID, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_UID, *m_Item, value, pos);
 }
 
-
-OFCondition ContentItemMacro::getTextValue(OFString &value,
-                                           const signed long pos) const
+OFCondition ContentItemMacro::getTextValue(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_TextValue, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_TextValue, *m_Item, value, pos);
 }
 
-
 CodeSequenceMacro* ContentItemMacro::getConceptCodeSequence()
 {
-  return m_ConceptCodeSequence.empty() ? OFnullptr : *m_ConceptCodeSequence.begin();
+    return m_ConceptCodeSequence.empty() ? OFnullptr : *m_ConceptCodeSequence.begin();
 }
 
 OFVector<CodeSequenceMacro*>& ContentItemMacro::getEntireConceptCodeSequence()
 {
-  return m_ConceptCodeSequence;
+    return m_ConceptCodeSequence;
 }
 
-
-OFCondition ContentItemMacro::getNumericValue(OFString &value,
-                                              const signed long pos) const
+OFCondition ContentItemMacro::getNumericValue(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_NumericValue, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_NumericValue, *m_Item, value, pos);
 }
 
-
-OFCondition ContentItemMacro::getFloatingPointValue(Float64 &value,
-                                                    const signed long pos) const
+OFCondition ContentItemMacro::getFloatingPointValue(Float64& value, const unsigned long pos) const
 {
-  return m_Item->findAndGetFloat64(DCM_FloatingPointValue, value, pos);
+    return m_Item->findAndGetFloat64(DCM_FloatingPointValue, value, pos);
 }
 
-
-OFCondition ContentItemMacro::getRationalNumeratorValue(Sint32 &value,
-                                                        const signed long pos) const
+OFCondition ContentItemMacro::getRationalNumeratorValue(Sint32& value, const unsigned long pos) const
 {
-  return m_Item->findAndGetSint32(DCM_RationalNumeratorValue, value, pos);
+    return m_Item->findAndGetSint32(DCM_RationalNumeratorValue, value, pos);
 }
 
-
-OFCondition ContentItemMacro::getRationalDenominatorValue(Uint32 &value,
-                                                          const signed long pos) const
+OFCondition ContentItemMacro::getRationalDenominatorValue(Uint32& value, const unsigned long pos) const
 {
-  return m_Item->findAndGetUint32(DCM_RationalDenominatorValue, value, pos);
+    return m_Item->findAndGetUint32(DCM_RationalDenominatorValue, value, pos);
 }
 
-
 CodeSequenceMacro* ContentItemMacro::getMeasurementUnitsCodeSequence()
 {
-  return m_MeasurementUnitsCodeSequence.empty() ? OFnullptr : *m_MeasurementUnitsCodeSequence.begin();
+    return m_MeasurementUnitsCodeSequence.empty() ? OFnullptr : *m_MeasurementUnitsCodeSequence.begin();
 }
 
 OFVector<CodeSequenceMacro*>& ContentItemMacro::getEntireMeasurementUnitsCodeSequence()
 {
-  return m_MeasurementUnitsCodeSequence;
+    return m_MeasurementUnitsCodeSequence;
 }
 
-
 ContentItemMacro::ReferencedSOPSequenceItem* ContentItemMacro::getReferencedSOPSequence()
 {
-  return m_ReferencedSOPSequence.empty() ? OFnullptr : *m_ReferencedSOPSequence.begin();
+    return m_ReferencedSOPSequence.empty() ? OFnullptr : *m_ReferencedSOPSequence.begin();
 }
 
 OFVector<ContentItemMacro::ReferencedSOPSequenceItem*>& ContentItemMacro::getEntireReferencedSOPSequence()
 {
-  return m_ReferencedSOPSequence;
+    return m_ReferencedSOPSequence;
 }
 
-
-OFCondition ContentItemMacro::setValueType(const OFString &value,
-                                           const OFBool checkValue)
+OFCondition ContentItemMacro::setValueType(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_ValueType, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_ValueType, value);
+    return result;
 }
 
-
-OFCondition ContentItemMacro::setValueType(const ContentItemMacro::ValueType value,
-                                           const OFBool checkValue)
+OFCondition ContentItemMacro::setValueType(const ContentItemMacro::ValueType value, const OFBool checkValue)
 {
-  (void)checkValue;
-  OFCondition result;
-  switch (value)
-  {
-    case VT_DATE:
+    (void)checkValue;
+    OFCondition result;
+    switch (value)
     {
-      result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "DATE");
-      break;
-    }
-    case VT_TIME:
-    {
-      result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "TIME");
-      break;
-    }
-    case VT_DATETIME:
-    {
-      result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "DATETIME");
-      break;
-    }
-    case VT_PNAME:
-    {
-      result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "PNAME");
-      break;
-    }
-    case VT_UIDREF:
-    {
-      result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "UIDREF");
-      break;
-    }
-    case VT_TEXT:
-    {
-      result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "TEXT");
-      break;
-    }
-    case VT_CODE:
-    {
-      result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "CODE");
-      break;
-    }
-    case VT_NUMERIC:
-    {
-      result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "NUMERIC");
-      break;
-    }
-    case VT_COMPOSITE:
-    {
-      result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "COMPOSITE");
-      break;
-    }
-    case VT_IMAGE:
-    {
-      result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "IMAGE");
-      break;
-    }
-    default:
-    {
-      result = IOD_EC_InvalidElementValue;
+        case VT_DATE:
+        {
+            result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "DATE");
+            break;
+        }
+        case VT_TIME:
+        {
+            result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "TIME");
+            break;
+        }
+        case VT_DATETIME:
+        {
+            result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "DATETIME");
+            break;
+        }
+        case VT_PNAME:
+        {
+            result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "PNAME");
+            break;
+        }
+        case VT_UIDREF:
+        {
+            result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "UIDREF");
+            break;
+        }
+        case VT_TEXT:
+        {
+            result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "TEXT");
+            break;
+        }
+        case VT_CODE:
+        {
+            result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "CODE");
+            break;
+        }
+        case VT_NUMERIC:
+        {
+            result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "NUMERIC");
+            break;
+        }
+        case VT_COMPOSITE:
+        {
+            result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "COMPOSITE");
+            break;
+        }
+        case VT_IMAGE:
+        {
+            result = m_Item->putAndInsertOFStringArray(DCM_ValueType, "IMAGE");
+            break;
+        }
+        default:
+        {
+            result = IOD_EC_InvalidElementValue;
+        }
     }
-  }
-  return result;
+    return result;
 }
 
-
-
-OFCondition ContentItemMacro::setDateTime(const OFString &value,
-                                          const OFBool checkValue)
+OFCondition ContentItemMacro::setDateTime(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDateTime::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_DateTime, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDateTime::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_DateTime, value);
+    return result;
 }
 
-
-OFCondition ContentItemMacro::setDate(const OFString &value,
-                                      const OFBool checkValue)
+OFCondition ContentItemMacro::setDate(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDate::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_Date, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDate::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_Date, value);
+    return result;
 }
 
-
-OFCondition ContentItemMacro::setTime(const OFString &value,
-                                      const OFBool checkValue)
+OFCondition ContentItemMacro::setTime(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmTime::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_Time, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmTime::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_Time, value);
+    return result;
 }
 
-
-OFCondition ContentItemMacro::setPersonName(const OFString &value,
-                                            const OFBool checkValue)
+OFCondition ContentItemMacro::setPersonName(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmPersonName::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_PersonName, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmPersonName::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_PersonName, value);
+    return result;
 }
 
-
-OFCondition ContentItemMacro::setUID(const OFString &value,
-                                     const OFBool checkValue)
+OFCondition ContentItemMacro::setUID(const OFString& value, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertOFStringArray(DCM_UID, value);
+    (void)checkValue;
+    return m_Item->putAndInsertOFStringArray(DCM_UID, value);
 }
 
-
-OFCondition ContentItemMacro::setTextValue(const OFString &value,
-                                           const OFBool checkValue)
+OFCondition ContentItemMacro::setTextValue(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUnlimitedText::checkStringValue(value) : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_TextValue, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmUnlimitedText::checkStringValue(value) : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_TextValue, value);
+    return result;
 }
 
-
-OFCondition ContentItemMacro::setNumericValue(const OFString &value,
-                                              const OFBool checkValue)
+OFCondition ContentItemMacro::setNumericValue(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1-n") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_NumericValue, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1-n") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_NumericValue, value);
+    return result;
 }
 
-
-OFCondition ContentItemMacro::setFloatingPointValue(const Float64 value,
-                                                    const unsigned long pos,
-                                                    const OFBool checkValue)
+OFCondition
+ContentItemMacro::setFloatingPointValue(const Float64 value, const unsigned long pos, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertFloat64(DCM_FloatingPointValue, value, pos);
+    (void)checkValue;
+    return m_Item->putAndInsertFloat64(DCM_FloatingPointValue, value, pos);
 }
 
-
-OFCondition ContentItemMacro::setRationalNumeratorValue(const Sint32 value,
-                                                        const unsigned long pos,
-                                                        const OFBool checkValue)
+OFCondition
+ContentItemMacro::setRationalNumeratorValue(const Sint32 value, const unsigned long pos, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertSint32(DCM_RationalNumeratorValue, value, pos);
+    (void)checkValue;
+    return m_Item->putAndInsertSint32(DCM_RationalNumeratorValue, value, pos);
 }
 
-
-OFCondition ContentItemMacro::setRationalDenominatorValue(const Uint32 value,
-                                                          const unsigned long pos,
-                                                          const OFBool checkValue)
+OFCondition
+ContentItemMacro::setRationalDenominatorValue(const Uint32 value, const unsigned long pos, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertUint32(DCM_RationalDenominatorValue, value, pos);
+    (void)checkValue;
+    return m_Item->putAndInsertUint32(DCM_RationalDenominatorValue, value, pos);
 }
 
-
 OFString ContentItemMacro::toString()
 {
-  ValueType vt;
-  getValueType(vt);
-  OFStringStream oss;
-  if (getConceptNameCodeSequence())
-  {
-    oss << getConceptNameCodeSequence()->toString() << ": ";
-  }
-  else
-  {
-    oss << "<no name>: ";
-  }
-  switch (vt)
-  {
-    case VT_CODE:
-      oss << "CODE: " << getConceptCodeSequence()->toString();
-      break;
-    case VT_COMPOSITE:
+    ValueType vt;
+    getValueType(vt);
+    OFStringStream oss;
+    if (getConceptNameCodeSequence())
     {
-      OFString sopClass, sopInstance, frameNumber;
-      if (getReferencedSOPSequence())
-      {
-        getReferencedSOPSequence()->getSOPInstanceReferenceMacro().getReferencedSOPClassUID(sopClass);
-        getReferencedSOPSequence()->getSOPInstanceReferenceMacro().getReferencedSOPClassUID(sopInstance);
-        getReferencedSOPSequence()->getReferencedFrameNumber(frameNumber);
-        oss << "COMPOSITE: " << sopClass << " / " << sopInstance;
-        if (!frameNumber.empty())
-        {
-          oss << " / Frames: " << frameNumber;
-        }
-        Uint16 val,pos;
-        val = pos = 0;
-        if (getReferencedSOPSequence()->getReferencedSegmentNumber(val, pos).good())
-        {
-          oss << " / Segments: ";
-          while (getReferencedSOPSequence()->getReferencedSegmentNumber(val, pos).good())
-          {
-            oss << val << " ";
-            pos++;
-          }
-        }
-      }
-      else
-      {
-        oss << "COMPOSITE: <None>";
-      }
-      break;
+        oss << getConceptNameCodeSequence()->toString() << ": ";
     }
-    case VT_DATE:
-    {
-      OFString date;
-      getDate(date);
-      oss << "DATE: " << date;
-      break;
-    }
-    case VT_DATETIME:
+    else
     {
-      OFString datetime;
-      getDateTime(datetime);
-      oss << "DATETIME: " << datetime;
-      break;
+        oss << "<no name>: ";
     }
-    case VT_IMAGE:
+    switch (vt)
     {
-      OFString sopClass, sopInstance, frameNumber;
-      if (getReferencedSOPSequence())
-      {
-        getReferencedSOPSequence()->getSOPInstanceReferenceMacro().getReferencedSOPClassUID(sopClass);
-        getReferencedSOPSequence()->getSOPInstanceReferenceMacro().getReferencedSOPClassUID(sopInstance);
-        getReferencedSOPSequence()->getReferencedFrameNumber(frameNumber);
-        oss << "IMAGE: " << sopClass << " / " << sopInstance;
-        if (!frameNumber.empty())
+        case VT_CODE:
+            oss << "CODE: " << getConceptCodeSequence()->toString();
+            break;
+        case VT_COMPOSITE:
         {
-          oss << " / Frames: " << frameNumber;
+            OFString sopClass, sopInstance, frameNumber;
+            if (getReferencedSOPSequence())
+            {
+                getReferencedSOPSequence()->getSOPInstanceReferenceMacro().getReferencedSOPClassUID(sopClass);
+                getReferencedSOPSequence()->getSOPInstanceReferenceMacro().getReferencedSOPClassUID(sopInstance);
+                getReferencedSOPSequence()->getReferencedFrameNumber(frameNumber);
+                oss << "COMPOSITE: " << sopClass << " / " << sopInstance;
+                if (!frameNumber.empty())
+                {
+                    oss << " / Frames: " << frameNumber;
+                }
+                Uint16 val, pos;
+                val = pos = 0;
+                if (getReferencedSOPSequence()->getReferencedSegmentNumber(val, pos).good())
+                {
+                    oss << " / Segments: ";
+                    while (getReferencedSOPSequence()->getReferencedSegmentNumber(val, pos).good())
+                    {
+                        oss << val << " ";
+                        pos++;
+                    }
+                }
+            }
+            else
+            {
+                oss << "COMPOSITE: <None>";
+            }
+            break;
         }
-      }
-      else
-      {
-        oss << "IMAGE: <None>";
-      }
-      break;
-    }
-    case VT_NUMERIC:
-    {
-      OFString val;
-      getNumericValue(val);
-      oss << "NUMERIC: " << val;
-      if (getMeasurementUnitsCodeSequence())
-      {
-        oss << ", Units: " << getMeasurementUnitsCodeSequence()->toString() << ")";
-      }
-      Uint16 pos =0;
-      Float64 fl64 = 0;
-      if (getFloatingPointValue(fl64, pos).good())
-      {
-        oss << ", Float value(s): " ;
-        do
+        case VT_DATE:
         {
-          oss << val << " ";
-          pos++;
-        } while (getFloatingPointValue(fl64, pos).good());
-      }
-      else
-      {
-        oss << ", Float value(s): <none>";
-      }
-      pos = 0;
-      Sint32 si32 = 0;
-      if (getRationalNumeratorValue(si32, pos).good())
-      {
-        oss << ", Numerator value(s): " ;
-        do
+            OFString date;
+            getDate(date);
+            oss << "DATE: " << date;
+            break;
+        }
+        case VT_DATETIME:
         {
-          oss << val << " ";
-          pos++;
-        } while (getRationalNumeratorValue(si32, pos).good());
-      }
-      pos = 0;
-      Uint32 ui32 = 0;
-      if (getRationalDenominatorValue(ui32, pos).good())
-      {
-        oss << ", Denominator value(s): " ;
-        do
+            OFString datetime;
+            getDateTime(datetime);
+            oss << "DATETIME: " << datetime;
+            break;
+        }
+        case VT_IMAGE:
         {
-          oss << val << " ";
-          pos++;
-        } while (getRationalDenominatorValue(ui32, pos).good());
-      }
-
-      break;
-    }
-    case VT_PNAME:
-    {
-      OFString val;
-      getPersonName(val);
-      oss << "PNAME: " << val;
-      break;
-    }
-    case VT_TEXT:
-    {
-      OFString val;
-      getTextValue(val);
-      oss << "TEXT: " << val;
-      break;
-    }
-    case VT_TIME:
-    {
-      OFString val;
-      getTime(val);
-      oss << "TIME: " << val;
-      break;
-    }
-    case VT_UIDREF:
-    {
-      OFString val;
-      getUID(val);
-      oss << "UIDREF: " << val;
-      break;
-    }
-    case VT_EMPTY:
-    {
-      oss << "<None>";
-      break;
-    }
-    case VT_UNKNOWN:
-    {
-      OFString val;
-      getValueType(val);
-      oss << "<Unknown: " << val << ">";
-      break;
-    }
-    default:
-    {
-      oss << "<Internal error>";
+            OFString sopClass, sopInstance, frameNumber;
+            if (getReferencedSOPSequence())
+            {
+                getReferencedSOPSequence()->getSOPInstanceReferenceMacro().getReferencedSOPClassUID(sopClass);
+                getReferencedSOPSequence()->getSOPInstanceReferenceMacro().getReferencedSOPClassUID(sopInstance);
+                getReferencedSOPSequence()->getReferencedFrameNumber(frameNumber);
+                oss << "IMAGE: " << sopClass << " / " << sopInstance;
+                if (!frameNumber.empty())
+                {
+                    oss << " / Frames: " << frameNumber;
+                }
+            }
+            else
+            {
+                oss << "IMAGE: <None>";
+            }
+            break;
+        }
+        case VT_NUMERIC:
+        {
+            OFString val;
+            getNumericValue(val);
+            oss << "NUMERIC: " << val;
+            if (getMeasurementUnitsCodeSequence())
+            {
+                oss << ", Units: " << getMeasurementUnitsCodeSequence()->toString() << ")";
+            }
+            Uint16 pos   = 0;
+            Float64 fl64 = 0;
+            if (getFloatingPointValue(fl64, pos).good())
+            {
+                oss << ", Float value(s): ";
+                do
+                {
+                    oss << val << " ";
+                    pos++;
+                } while (getFloatingPointValue(fl64, pos).good());
+            }
+            else
+            {
+                oss << ", Float value(s): <none>";
+            }
+            pos         = 0;
+            Sint32 si32 = 0;
+            if (getRationalNumeratorValue(si32, pos).good())
+            {
+                oss << ", Numerator value(s): ";
+                do
+                {
+                    oss << val << " ";
+                    pos++;
+                } while (getRationalNumeratorValue(si32, pos).good());
+            }
+            pos         = 0;
+            Uint32 ui32 = 0;
+            if (getRationalDenominatorValue(ui32, pos).good())
+            {
+                oss << ", Denominator value(s): ";
+                do
+                {
+                    oss << val << " ";
+                    pos++;
+                } while (getRationalDenominatorValue(ui32, pos).good());
+            }
+
+            break;
+        }
+        case VT_PNAME:
+        {
+            OFString val;
+            getPersonName(val);
+            oss << "PNAME: " << val;
+            break;
+        }
+        case VT_TEXT:
+        {
+            OFString val;
+            getTextValue(val);
+            oss << "TEXT: " << val;
+            break;
+        }
+        case VT_TIME:
+        {
+            OFString val;
+            getTime(val);
+            oss << "TIME: " << val;
+            break;
+        }
+        case VT_UIDREF:
+        {
+            OFString val;
+            getUID(val);
+            oss << "UIDREF: " << val;
+            break;
+        }
+        case VT_EMPTY:
+        {
+            oss << "<None>";
+            break;
+        }
+        case VT_UNKNOWN:
+        {
+            OFString val;
+            getValueType(val);
+            oss << "<Unknown: " << val << ">";
+            break;
+        }
+        default:
+        {
+            oss << "<Internal error>";
+        }
     }
-  }
-  OFSTRINGSTREAM_GETOFSTRING(oss, val);
-  return val;
+    OFSTRINGSTREAM_GETOFSTRING(oss, val);
+    return val;
 }
-
index e171bfd1b632007c82d57363f091222a0f375010..c93e21088bffb4b4ccf98a228ead9ee3c7a954bb 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2019, Open Connections GmbH
+ *  Copyright (C) 2015-2020, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/iodmacro.h"
-#include "dcmtk/dcmiod/iodutil.h" // for static IOD helpers
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+#include "dcmtk/dcmiod/iodutil.h"  // for static IOD helpers
 #include "dcmtk/ofstd/ofstream.h"
 
-
 // --------------------------- Code Sequence Macro ---------------------------
 
-
 // -- Code Sequence Macro
 
-CodeSequenceMacro::CodeSequenceMacro(OFshared_ptr<DcmItem> item,
-                                     OFshared_ptr<IODRules> rules,
-                                     IODComponent* parent)
-  : IODComponent(item, rules, parent)
+CodeSequenceMacro::CodeSequenceMacro(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules, IODComponent* parent)
+    : IODComponent(item, rules, parent)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
-CodeSequenceMacro::CodeSequenceMacro(IODComponent* parent) : IODComponent(parent)
+CodeSequenceMacro::CodeSequenceMacro(IODComponent* parent)
+    : IODComponent(parent)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 CodeSequenceMacro::CodeSequenceMacro(const CodeSequenceMacro& rhs)
-: IODComponent(rhs)
+    : IODComponent(rhs)
 {
 }
 
-
-
 CodeSequenceMacro::~CodeSequenceMacro()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
 CodeSequenceMacro::CodeSequenceMacro(const OFString& codeValue,
                                      const OFString& codingSchemeDesignator,
                                      const OFString& codeMeaning,
                                      const OFString& codingSchemeVersion,
                                      IODComponent* parent)
-: IODComponent(parent)
+    : IODComponent(parent)
+{
+    // reset element rules
+    resetRules();
+    set(codeValue, codingSchemeDesignator, codeMeaning, codingSchemeVersion);
+}
+
+OFCondition CodeSequenceMacro::check(const bool quiet)
 {
-  // reset element rules
-  resetRules();
-  setCodeValue(codeValue);
-  setCodeMeaning(codeMeaning);
-  setCodingSchemeDesignator(codingSchemeDesignator);
-  if (!codingSchemeVersion.empty())
-  {
-    setCodingSchemeVersion(codingSchemeVersion);
-  }
+    OFString val;
+    getCodeValue(val);
+    if (!val.empty())
+        getCodingSchemeDesignator(val);
+    if (!val.empty())
+        getCodeMeaning(val);
+    if (!val.empty())
+        return EC_Normal;
+
+    return EC_IllegalParameter;
 }
 
-CodeSequenceMacro::CodeSequenceMacro(OFshared_ptr< DcmItem > item,
-                                     OFshared_ptr< IODRules > rules,
+CodeSequenceMacro::CodeSequenceMacro(OFshared_ptr<DcmItem> item,
+                                     OFshared_ptr<IODRules> rules,
                                      IODComponent* parent,
                                      const OFString& codeValue,
                                      const OFString& codingSchemeDesignator,
                                      const OFString& codeMeaning,
                                      const OFString& codingSchemeVersion)
-: IODComponent(item, rules, parent)
+    : IODComponent(item, rules, parent)
 {
-  // reset element rules
-  resetRules();
-  setCodeValue(codeValue);
-  setCodeMeaning(codeMeaning);
-  setCodingSchemeDesignator(codingSchemeDesignator);
-  if (!codingSchemeVersion.empty())
-  {
-    setCodingSchemeVersion(codingSchemeVersion);
-  }
+    // reset element rules
+    resetRules();
+    set(codeValue, codingSchemeDesignator, codeMeaning, codingSchemeVersion);
 }
 
-
 OFString CodeSequenceMacro::getName() const
 {
-  return "CodeSequenceMacro";
+    return "CodeSequenceMacro";
 }
 
-
 void CodeSequenceMacro::resetRules()
 {
-  m_Rules->addRule(new IODRule(DCM_CodeValue, "1", "1", getName(), DcmIODTypes::IE_UNDEFINED), OFTrue /*overwrite old rule*/);
-  m_Rules->addRule(new IODRule(DCM_CodingSchemeDesignator, "1", "1", getName(), DcmIODTypes::IE_UNDEFINED), OFTrue /*overwrite old rule*/);
-  m_Rules->addRule(new IODRule(DCM_CodingSchemeVersion, "1", "1C", getName(), DcmIODTypes::IE_UNDEFINED), OFTrue /*overwrite old rule*/);
-  m_Rules->addRule(new IODRule(DCM_CodeMeaning, "1", "1", getName(), DcmIODTypes::IE_UNDEFINED), OFTrue /*overwrite old rule*/);
+    m_Rules->addRule(new IODRule(DCM_CodeValue, "1", "1C", getName(), DcmIODTypes::IE_UNDEFINED),
+                     OFTrue /*overwrite old rule*/);
+    m_Rules->addRule(new IODRule(DCM_URNCodeValue, "1", "1C", getName(), DcmIODTypes::IE_UNDEFINED),
+                     OFTrue /*overwrite old rule*/);
+    m_Rules->addRule(new IODRule(DCM_LongCodeValue, "1", "1C", getName(), DcmIODTypes::IE_UNDEFINED),
+                     OFTrue /*overwrite old rule*/);
+    m_Rules->addRule(new IODRule(DCM_CodingSchemeDesignator, "1", "1", getName(), DcmIODTypes::IE_UNDEFINED),
+                     OFTrue /*overwrite old rule*/);
+    m_Rules->addRule(new IODRule(DCM_CodingSchemeVersion, "1", "1C", getName(), DcmIODTypes::IE_UNDEFINED),
+                     OFTrue /*overwrite old rule*/);
+    m_Rules->addRule(new IODRule(DCM_CodeMeaning, "1", "1", getName(), DcmIODTypes::IE_UNDEFINED),
+                     OFTrue /*overwrite old rule*/);
 }
 
-
 // -- get dicom attributes --
 
-OFCondition CodeSequenceMacro::getCodeValue(OFString &value,
-                                            const signed long pos)
+OFCondition CodeSequenceMacro::getCodeValue(OFString& value, const signed long pos, const OFBool autoTag)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_CodeValue, *m_Item, value, pos);
-}
+    OFString c;
+    OFCondition cond = DcmIODUtil::getStringValueFromItem(DCM_CodeValue, *m_Item, value, pos);
+    if (cond.good() || ((cond == EC_TagNotFound) && !autoTag))
+        return cond;
 
+    cond = DcmIODUtil::getStringValueFromItem(DCM_URNCodeValue, *m_Item, value, pos);
+    if (cond != EC_TagNotFound)
+        return cond;
 
-OFCondition CodeSequenceMacro::getCodingSchemeDesignator(OFString &value,
-                                                         const signed long pos)
-{
-  return DcmIODUtil::getStringValueFromItem(DCM_CodingSchemeDesignator, *m_Item, value, pos);
+    cond = DcmIODUtil::getStringValueFromItem(DCM_LongCodeValue, *m_Item, value, pos);
+    return cond;
 }
 
-
-OFCondition CodeSequenceMacro::getCodingSchemeVersion(OFString &value,
-                                                      const signed long pos)
+OFCondition CodeSequenceMacro::getURNCodeValue(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_CodingSchemeVersion, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_URNCodeValue, *m_Item, value, pos);
+}
 
+OFCondition CodeSequenceMacro::getLongCodeValue(OFString& value, const signed long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_LongCodeValue, *m_Item, value, pos);
 }
 
+OFCondition CodeSequenceMacro::getCodingSchemeDesignator(OFString& value, const signed long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_CodingSchemeDesignator, *m_Item, value, pos);
+}
 
-OFCondition CodeSequenceMacro::getCodeMeaning(OFString &value,
-                                              const signed long pos)
+OFCondition CodeSequenceMacro::getCodingSchemeVersion(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_CodeMeaning, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_CodingSchemeVersion, *m_Item, value, pos);
 }
 
+OFCondition CodeSequenceMacro::getCodeMeaning(OFString& value, const signed long pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_CodeMeaning, *m_Item, value, pos);
+}
 
 OFBool CodeSequenceMacro::empty()
 {
-  OFString val;
-  getCodeValue(val);
-  if (val.empty())
-  {
-    getCodingSchemeDesignator(val);
+    OFString val;
+    getCodeValue(val);
     if (val.empty())
     {
-      getCodingSchemeVersion(val);
-      if (val.empty())
-      {
         getCodingSchemeDesignator(val);
         if (val.empty())
         {
-          return OFTrue;
+            getCodingSchemeVersion(val);
+            if (val.empty())
+            {
+                getCodingSchemeDesignator(val);
+                if (val.empty())
+                {
+                    return OFTrue;
+                }
+            }
         }
-      }
     }
-  }
-  return OFFalse;
+    return OFFalse;
 }
 
-
 // -- set dicom attributes --
 
-OFCondition CodeSequenceMacro::setCodeValue(const OFString &value,
-                                            const OFBool checkValue)
+OFCondition CodeSequenceMacro::setCodeValue(const OFString& value, const OFBool checkValue, const OFBool autoTag)
 {
-  OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
+    OFCondition result;
+
+    // Identify the code value tag to be used
+    if (autoTag)
+    {
+        if ((value.find("://") != OFString_npos) || (value.compare(0, 4, "urn:") == 0))
+        {
+            return setURNCodeValue(value, checkValue);
+        }
+        else if (value.length() > 16) // Long Code Value
+        {
+            return setLongCodeValue(value, checkValue);
+        }
+    }
+    // Classic Code Value
+    result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
+    if (result.bad())
+        return result;
+    // TODO: Should check length in characters (not bytes), since SH permits usage of
+    // non-ASCII characters (i.e. as defined in 0008,0015).
+    if (value.length() > 16)
+        return EC_MaximumLengthViolated;
     result = m_Item->putAndInsertOFStringArray(DCM_CodeValue, value);
-  return result;
+    if (result.good())
+    {
+        deleteUnusedCodeValues(DCM_CodeValue);
+    }
+    return result;
 }
 
-OFCondition CodeSequenceMacro::setCodingSchemeDesignator(const OFString &value,
-                                                         const OFBool checkValue)
+OFCondition CodeSequenceMacro::setURNCodeValue(const OFString& value, const bool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_CodingSchemeDesignator, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmUniversalResourceIdentifierOrLocator::checkStringValue(value) : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_URNCodeValue, value);
+    if (result.good())
+    {
+        deleteUnusedCodeValues(DCM_URNCodeValue);
+    }
+    return result;
 }
 
-OFCondition CodeSequenceMacro::setCodingSchemeVersion(const OFString &value,
-                                                      const OFBool checkValue)
+OFCondition CodeSequenceMacro::setLongCodeValue(const OFString& value, const bool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1C") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_CodingSchemeVersion, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmUnlimitedCharacters::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_LongCodeValue, value);
+    if (result.good())
+    {
+        deleteUnusedCodeValues(DCM_LongCodeValue);
+    }
+    return result;
 }
 
-OFCondition CodeSequenceMacro::setCodeMeaning(const OFString &value,
-                                              const OFBool checkValue)
+OFCondition CodeSequenceMacro::setCodingSchemeDesignator(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_CodeMeaning, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_CodingSchemeDesignator, value);
+    return result;
 }
 
+OFCondition CodeSequenceMacro::setCodingSchemeVersion(const OFString& value, const OFBool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_CodingSchemeVersion, value);
+    return result;
+}
+
+OFCondition CodeSequenceMacro::setCodeMeaning(const OFString& value, const OFBool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_CodeMeaning, value);
+    return result;
+}
 
 OFCondition CodeSequenceMacro::set(const OFString& value,
                                    const OFString& scheme,
                                    const OFString& meaning,
                                    const OFString& schemeVersion,
-                                   const OFBool checkValue)
+                                   const OFBool checkValue,
+                                   const OFBool autoTag)
 {
-  if (checkValue)
-  {
-    if (value.empty() || scheme.empty() || meaning.empty() )
-    {
-      DCMIOD_ERROR("Could not set code since Code Value, Coding Scheme Designator and Code Meaning must have non-empty values");
-      return IOD_EC_InvalidElementValue;
-    }
-  }
-  OFCondition result = setCodeValue(value, checkValue);
-  if (result.good()) result = setCodingSchemeDesignator(scheme, checkValue);
-  if (result.good()) result = setCodeMeaning(meaning, checkValue);
-  if (result.good() && !schemeVersion.empty()) result = setCodingSchemeVersion(schemeVersion, checkValue);
-  return result;
+    OFCondition result;
+    result = setCodeValue(value, checkValue, autoTag);
+    if (result.good())
+        result = setCodingSchemeDesignator(scheme, checkValue);
+    if (result.good())
+        result = setCodeMeaning(meaning, checkValue);
+    if (result.good() && !schemeVersion.empty())
+        result = setCodingSchemeVersion(schemeVersion, checkValue);
+    return result;
 }
 
+void CodeSequenceMacro::deleteUnusedCodeValues(const DcmTagKey& keepTag)
+{
+    if (keepTag != DCM_CodeValue)
+        m_Item->findAndDeleteElement(DCM_CodeValue);
+    if (keepTag != DCM_URNCodeValue)
+        m_Item->findAndDeleteElement(DCM_URNCodeValue);
+    if (keepTag != DCM_LongCodeValue)
+        m_Item->findAndDeleteElement(DCM_LongCodeValue);
+}
 
 // ---------------------- CodeWithModifiers----------------------
 
 CodeWithModifiers::CodeWithModifiers(const OFString& modifierType,
                                      const OFString& modifierVM,
                                      const DcmTagKey& modifierSeq)
-: CodeSequenceMacro(),
-  m_Modifiers(),
-  m_ModifierType(modifierType),
-  m_ModifierVM(modifierVM),
-  m_CodeModifierSeq(modifierSeq)
+    : CodeSequenceMacro()
+    , m_Modifiers()
+    , m_ModifierType(modifierType)
+    , m_ModifierVM(modifierVM)
+    , m_CodeModifierSeq(modifierSeq)
 {
-  resetRules();
+    resetRules();
 }
 
-
 CodeWithModifiers::CodeWithModifiers(const CodeWithModifiers& rhs)
-: CodeSequenceMacro(rhs),
-  m_Modifiers(),
-  m_ModifierType(),
-  m_ModifierVM(),
-  m_CodeModifierSeq()
+    : CodeSequenceMacro(rhs)
+    , m_Modifiers()
+    , m_ModifierType()
+    , m_ModifierVM()
+    , m_CodeModifierSeq()
 {
-  if (&rhs == this)
-    return;
+    if (&rhs == this)
+        return;
 
-  *this = rhs;
+    *this = rhs;
 }
 
-
 CodeWithModifiers& CodeWithModifiers::operator=(const CodeWithModifiers& rhs)
 {
-  if (&rhs == this)
-    return *this;
+    if (&rhs == this)
+        return *this;
 
-  CodeSequenceMacro::operator=(rhs);
+    CodeSequenceMacro::operator=(rhs);
 
-  const CodeWithModifiers* r = OFstatic_cast(const CodeWithModifiers*, &rhs);
-  if (r)
-  {
-    OFVector<CodeSequenceMacro*>::const_iterator it = r->m_Modifiers.begin();
-    while ((it != r->m_Modifiers.end()))
+    const CodeWithModifiers* r = OFstatic_cast(const CodeWithModifiers*, &rhs);
+    if (r)
     {
-      m_Modifiers.push_back(new CodeSequenceMacro(*it));
-      it++;
+        OFVector<CodeSequenceMacro*>::const_iterator it = r->m_Modifiers.begin();
+        while ((it != r->m_Modifiers.end()))
+        {
+            m_Modifiers.push_back(new CodeSequenceMacro(*it));
+            it++;
+        }
     }
-  }
 
-  return *this;
+    return *this;
 }
 
-
 OFCondition CodeWithModifiers::check(const OFBool quiet)
 {
-  OFCondition result = CodeSequenceMacro::check(quiet);
-  if (result.good())
-  {
-    OFVector<CodeSequenceMacro*>::iterator it = m_Modifiers.begin();
-    while (result.good() && (it != m_Modifiers.end()))
+    OFCondition result = CodeSequenceMacro::check(quiet);
+    if (result.good())
     {
-      result = (*it)->check(quiet);
-      it++;
+        OFVector<CodeSequenceMacro*>::iterator it = m_Modifiers.begin();
+        while (result.good() && (it != m_Modifiers.end()))
+        {
+            result = (*it)->check(quiet);
+            it++;
+        }
     }
-  }
-  if (result.bad())
-  {
-    if (!quiet)
+    if (result.bad())
     {
-      DCMIOD_ERROR("Invalid code in Code Sequence Macro or its modifiers");
+        if (!quiet)
+        {
+            DCMIOD_ERROR("Invalid code in Code Sequence Macro or its modifiers");
+        }
     }
-  }
-  return result;
+    return result;
 }
 
-
 void CodeWithModifiers::clearData()
 {
-  CodeSequenceMacro::clearData();
-  DcmIODUtil::freeContainer(m_Modifiers);
+    CodeSequenceMacro::clearData();
+    DcmIODUtil::freeContainer(m_Modifiers);
 }
 
-
 int CodeWithModifiers::compare(const IODComponent& rhs) const
 {
-  const CodeWithModifiers* r = OFstatic_cast(const CodeWithModifiers*, &rhs);
-  if (!r)
-    return -1;
+    const CodeWithModifiers* r = OFstatic_cast(const CodeWithModifiers*, &rhs);
+    if (!r)
+        return -1;
 
-  if (m_Modifiers.size() < r->m_Modifiers.size())
-    return -1;
-  else if (m_Modifiers.size() > r->m_Modifiers.size())
-    return 1;
+    if (m_Modifiers.size() < r->m_Modifiers.size())
+        return -1;
+    else if (m_Modifiers.size() > r->m_Modifiers.size())
+        return 1;
 
-  int result = IODComponent::compare(*r);
-  if (result == 0)
-  {
-    for (size_t n = 0; (n < m_Modifiers.size()) && (result == 0);  n++)
+    int result = IODComponent::compare(*r);
+    if (result == 0)
     {
-      result = m_Modifiers[n]->compare(*r->m_Modifiers[n]);
+        for (size_t n = 0; (n < m_Modifiers.size()) && (result == 0); n++)
+        {
+            result = m_Modifiers[n]->compare(*r->m_Modifiers[n]);
+        }
     }
-  }
-  return result;
+    return result;
 }
 
-
 OFString CodeWithModifiers::getName() const
 {
-  return "CodeWithModifiers";
+    return "CodeWithModifiers";
 }
 
-
 OFCondition CodeWithModifiers::addModifier(const CodeSequenceMacro& modifier)
 {
-  OFCondition result = OFconst_cast(CodeSequenceMacro*, &modifier)->check();
-  if (result.good())
-  {
-    m_Modifiers.push_back(new CodeSequenceMacro(modifier));
-  }
-  return result;
+    OFCondition result = OFconst_cast(CodeSequenceMacro*, &modifier)->check();
+    if (result.good())
+    {
+        m_Modifiers.push_back(new CodeSequenceMacro(modifier));
+    }
+    return result;
 }
 
-
 CodeSequenceMacro* CodeWithModifiers::getModifier(const size_t index)
 {
-  if (index + 1 > m_Modifiers.size())
-    return NULL;
-  else
-    return m_Modifiers[index];
+    if (index + 1 > m_Modifiers.size())
+        return NULL;
+    else
+        return m_Modifiers[index];
 }
 
-
-OFCondition CodeWithModifiers::read(DcmItem& source,
-                                    const OFBool clearOldData)
+OFCondition CodeWithModifiers::read(DcmItem& source, const OFBool clearOldData)
 {
-  OFCondition result = CodeSequenceMacro::read(source, clearOldData);
-  if (result.good() && clearOldData)
-  {
-    DcmIODUtil::freeContainer(m_Modifiers);
-  }
-  if (result.good())
-  {
-    result = DcmIODUtil::readSubSequence(source, m_CodeModifierSeq, m_Modifiers, getRules()->getByTag(m_CodeModifierSeq));
-  }
-  return result;
+    OFCondition result = CodeSequenceMacro::read(source, clearOldData);
+    if (result.good() && clearOldData)
+    {
+        DcmIODUtil::freeContainer(m_Modifiers);
+    }
+    if (result.good())
+    {
+        result = DcmIODUtil::readSubSequence(
+            source, m_CodeModifierSeq, m_Modifiers, getRules()->getByTag(m_CodeModifierSeq));
+    }
+    return result;
 }
 
-
 void CodeWithModifiers::resetRules()
 {
-  CodeSequenceMacro::resetRules();
-  m_Rules->addRule(new IODRule(m_CodeModifierSeq, m_ModifierVM, m_ModifierType, getName(), DcmIODTypes::IE_UNDEFINED));
+    CodeSequenceMacro::resetRules();
+    m_Rules->addRule(
+        new IODRule(m_CodeModifierSeq, m_ModifierVM, m_ModifierType, getName(), DcmIODTypes::IE_UNDEFINED));
 }
 
-
 OFCondition CodeWithModifiers::write(DcmItem& destination)
 {
-  OFCondition result;
-  DcmIODUtil::writeSubSequence(result, m_CodeModifierSeq, m_Modifiers, getData(), getRules()->getByTag(m_CodeModifierSeq));
-  if (result.good())
-  {
-    result = CodeSequenceMacro::write(destination);
-  }
-  return result;
+    OFCondition result;
+    DcmIODUtil::writeSubSequence(
+        result, m_CodeModifierSeq, m_Modifiers, getData(), getRules()->getByTag(m_CodeModifierSeq));
+    if (result.good())
+    {
+        result = CodeSequenceMacro::write(destination);
+    }
+    return result;
 }
 
-
 CodeWithModifiers::~CodeWithModifiers()
 {
-  DcmIODUtil::freeContainer(m_Modifiers);
+    DcmIODUtil::freeContainer(m_Modifiers);
 }
 
-
 OFString CodeSequenceMacro::toString()
 {
-  OFString d,m,v;
-  getCodeValue(v);
-  getCodeMeaning(m);
-  getCodingSchemeDesignator(d);
-  OFStringStream oss;
-  oss << "(" << d << "," << v << "," << m << ")";
-  OFSTRINGSTREAM_GETOFSTRING(oss, msg);
-  return msg;
-
+    OFString d, m, v;
+    getCodeValue(v);
+    getCodeMeaning(m);
+    getCodingSchemeDesignator(d);
+    OFStringStream oss;
+    oss << "(" << d << "," << v << "," << m << ")";
+    OFSTRINGSTREAM_GETOFSTRING(oss, msg);
+    return msg;
 }
 
-
 // ---------------------- SeriesAndInstanceReferenceMacro----------------------
 
 const OFString IODSeriesAndInstanceReferenceMacro::m_ComponentName = "SeriesAndInstanceReferenceMacro";
-const OFString IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::m_ComponentName = "SeriesAndInstanceReferenceMacro";
+const OFString IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::m_ComponentName
+    = "SeriesAndInstanceReferenceMacro";
 
-IODSeriesAndInstanceReferenceMacro::IODSeriesAndInstanceReferenceMacro(OFshared_ptr< DcmItem > data,
-                                                                       OFshared_ptr< IODRules > rules,
-                                                                       IODComponent* parent) :
-  IODComponent(data, rules, parent),
-  m_ReferencedSeriesItems()
+IODSeriesAndInstanceReferenceMacro::IODSeriesAndInstanceReferenceMacro(OFshared_ptr<DcmItem> data,
+                                                                       OFshared_ptr<IODRules> rules,
+                                                                       IODComponent* parent)
+    : IODComponent(data, rules, parent)
+    , m_ReferencedSeriesItems()
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
-IODSeriesAndInstanceReferenceMacro::IODSeriesAndInstanceReferenceMacro(IODComponent* parent) :
-  IODComponent(parent),
-  m_ReferencedSeriesItems()
+IODSeriesAndInstanceReferenceMacro::IODSeriesAndInstanceReferenceMacro(IODComponent* parent)
+    : IODComponent(parent)
+    , m_ReferencedSeriesItems()
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 OFString IODSeriesAndInstanceReferenceMacro::getName() const
 {
-  return m_ComponentName;
+    return m_ComponentName;
 }
 
-
-OFCondition IODSeriesAndInstanceReferenceMacro::read(DcmItem& source,
-                                                     const OFBool clearOldData)
+OFCondition IODSeriesAndInstanceReferenceMacro::read(DcmItem& source, const OFBool clearOldData)
 {
-  if (clearOldData)
-    clearData();
+    if (clearOldData)
+        clearData();
 
-  DcmIODUtil::readSubSequence<OFVector<ReferencedSeriesItem*> >(source, DCM_ReferencedSeriesSequence, m_ReferencedSeriesItems, m_Rules->getByTag(DCM_ReferencedSeriesSequence));
-  return EC_Normal;
+    DcmIODUtil::readSubSequence<OFVector<ReferencedSeriesItem*> >(
+        source, DCM_ReferencedSeriesSequence, m_ReferencedSeriesItems, m_Rules->getByTag(DCM_ReferencedSeriesSequence));
+    return EC_Normal;
 }
 
-
 OFCondition IODSeriesAndInstanceReferenceMacro::write(DcmItem& destination)
 {
-  OFCondition result = EC_Normal;
+    OFCondition result = EC_Normal;
 
-  DcmIODUtil::writeSubSequence<OFVector<ReferencedSeriesItem*> >(result, DCM_ReferencedSeriesSequence, m_ReferencedSeriesItems, destination, m_Rules->getByTag(DCM_ReferencedSeriesSequence));
+    DcmIODUtil::writeSubSequence<OFVector<ReferencedSeriesItem*> >(result,
+                                                                   DCM_ReferencedSeriesSequence,
+                                                                   m_ReferencedSeriesItems,
+                                                                   destination,
+                                                                   m_Rules->getByTag(DCM_ReferencedSeriesSequence));
 
-  return result;
+    return result;
 }
 
-
 void IODSeriesAndInstanceReferenceMacro::clearData()
 {
-  DcmIODUtil::freeContainer(m_ReferencedSeriesItems);
+    DcmIODUtil::freeContainer(m_ReferencedSeriesItems);
 }
 
-
 void IODSeriesAndInstanceReferenceMacro::resetRules()
 {
-  m_Rules->addRule(new IODRule(DCM_ReferencedSeriesSequence, "1-n", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ReferencedSeriesSequence, "1-n", "1", getName(), DcmIODTypes::IE_INSTANCE),
+                     OFTrue);
 }
 
-
-OFVector< IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem* >& IODSeriesAndInstanceReferenceMacro::getReferencedSeriesItems()
+OFVector<IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem*>&
+IODSeriesAndInstanceReferenceMacro::getReferencedSeriesItems()
 {
-  return m_ReferencedSeriesItems;
+    return m_ReferencedSeriesItems;
 }
 
-
 IODSeriesAndInstanceReferenceMacro::~IODSeriesAndInstanceReferenceMacro()
 {
-  DcmIODUtil::freeContainer(m_ReferencedSeriesItems);
+    DcmIODUtil::freeContainer(m_ReferencedSeriesItems);
 }
 
-
-IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::ReferencedSeriesItem(OFshared_ptr< DcmItem > item,
-                                                                              OFshared_ptr< IODRules > rules,
-                                                                              IODComponent* parent)
-: IODComponent(item, rules, parent),
-  m_ReferencedInstanceSequence()
+IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::ReferencedSeriesItem(OFshared_ptr<DcmItem> item,
+                                                                               OFshared_ptr<IODRules> rules,
+                                                                               IODComponent* parent)
+    : IODComponent(item, rules, parent)
+    , m_ReferencedInstanceSequence()
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::ReferencedSeriesItem(IODComponent* parent)
-: IODComponent(parent),
-  m_ReferencedInstanceSequence()
+    : IODComponent(parent)
+    , m_ReferencedInstanceSequence()
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::~ReferencedSeriesItem()
 {
-  clearData();
+    clearData();
 }
 
-
 OFString IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::getName() const
 {
-  return m_ComponentName;
+    return m_ComponentName;
 }
 
-
 void IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::clearData()
 {
-  DcmIODUtil::freeContainer(m_ReferencedInstanceSequence);
-  IODComponent::clearData();
+    DcmIODUtil::freeContainer(m_ReferencedInstanceSequence);
+    IODComponent::clearData();
 }
 
-
-
-OFCondition IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::read(DcmItem& source,
-                                                                           const OFBool clearOldData)
+OFCondition IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::read(DcmItem& source, const OFBool clearOldData)
 {
-  if (clearOldData)
-    clearData();
+    if (clearOldData)
+        clearData();
 
-  IODComponent::read(source, clearOldData);
-  DcmIODUtil::readSubSequence(source, DCM_ReferencedInstanceSequence, m_ReferencedInstanceSequence, m_Rules->getByTag(DCM_ReferencedInstanceSequence));
-  return EC_Normal;
+    IODComponent::read(source, clearOldData);
+    DcmIODUtil::readSubSequence(source,
+                                DCM_ReferencedInstanceSequence,
+                                m_ReferencedInstanceSequence,
+                                m_Rules->getByTag(DCM_ReferencedInstanceSequence));
+    return EC_Normal;
 }
 
-
 OFCondition IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::write(DcmItem& destination)
 {
-  OFCondition result = EC_Normal;
+    OFCondition result = EC_Normal;
 
-  DcmIODUtil::writeSubSequence<OFVector<SOPInstanceReferenceMacro*> >(result, DCM_ReferencedInstanceSequence, m_ReferencedInstanceSequence, *m_Item, m_Rules->getByTag(DCM_ReferencedInstanceSequence));
-  result = IODComponent::write(destination);
+    DcmIODUtil::writeSubSequence<OFVector<SOPInstanceReferenceMacro*> >(
+        result,
+        DCM_ReferencedInstanceSequence,
+        m_ReferencedInstanceSequence,
+        *m_Item,
+        m_Rules->getByTag(DCM_ReferencedInstanceSequence));
+    result = IODComponent::write(destination);
 
-  return result;
+    return result;
 }
 
-
 void IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::resetRules()
 {
-  // Parameters for Rule are tag, VM, type (1,1C,2,2C,3), module name and logical IOD level
-  m_Rules->addRule(new IODRule(DCM_SeriesInstanceUID, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ReferencedInstanceSequence, "1-n", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    // Parameters for Rule are tag, VM, type (1,1C,2,2C,3), module name and logical IOD level
+    m_Rules->addRule(new IODRule(DCM_SeriesInstanceUID, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ReferencedInstanceSequence, "1-n", "1", getName(), DcmIODTypes::IE_INSTANCE),
+                     OFTrue);
 }
 
-
-OFVector< SOPInstanceReferenceMacro* >& IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::getReferencedInstanceItems()
+OFVector<SOPInstanceReferenceMacro*>&
+IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::getReferencedInstanceItems()
 {
-  return m_ReferencedInstanceSequence;
+    return m_ReferencedInstanceSequence;
 }
 
-
-OFCondition IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::getSeriesInstanceUID(OFString& value,
-                                                                                         const long signed int pos) const
+OFCondition
+IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::getSeriesInstanceUID(OFString& value,
+                                                                               const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_SeriesInstanceUID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_SeriesInstanceUID, *m_Item, value, pos);
 }
 
-
 OFCondition IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::setSeriesInstanceUID(const OFString& value,
                                                                                            const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_SeriesInstanceUID, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_SeriesInstanceUID, value);
+    return result;
 }
 
-OFCondition IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::addReference(
-  const OFString& sopClassUID,
-  const OFString& sopInstanceUID)
+OFCondition IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem::addReference(const OFString& sopClassUID,
+                                                                                   const OFString& sopInstanceUID)
 {
-  OFVector<SOPInstanceReferenceMacro*>::iterator instance = m_ReferencedInstanceSequence.begin();
-  while (instance != m_ReferencedInstanceSequence.end())
-  {
-    OFString c,i;
-    (*instance)->getReferencedSOPClassUID(c);
-    (*instance)->getReferencedSOPInstanceUID(i);
-    if ( i == sopInstanceUID)
+    OFVector<SOPInstanceReferenceMacro*>::iterator instance = m_ReferencedInstanceSequence.begin();
+    while (instance != m_ReferencedInstanceSequence.end())
     {
-      DCMIOD_DEBUG("Skipping doubled instance reference when adding to Series and Instance Reference Macro");
-      return EC_Normal;
+        OFString c, i;
+        (*instance)->getReferencedSOPClassUID(c);
+        (*instance)->getReferencedSOPInstanceUID(i);
+        if (i == sopInstanceUID)
+        {
+            DCMIOD_DEBUG("Skipping doubled instance reference when adding to Series and Instance Reference Macro");
+            return EC_Normal;
+        }
+        else
+        {
+            instance++;
+        }
+    }
+    // We get here in case that we do not have this reference, add new one
+    SOPInstanceReferenceMacro* macro = new SOPInstanceReferenceMacro();
+    if (!macro)
+    {
+        return EC_MemoryExhausted;
+    }
+    OFCondition result = macro->setReferencedSOPClassUID(sopClassUID);
+    if (result.good())
+        result = macro->setReferencedSOPInstanceUID(sopInstanceUID);
+    if (result.good())
+    {
+        m_ReferencedInstanceSequence.push_back(macro);
     }
     else
     {
-      instance++;
+        delete macro;
+        result = IOD_EC_InvalidElementValue;
     }
-  }
-  // We get here in case that we do not have this reference, add new one
-  SOPInstanceReferenceMacro* macro = new SOPInstanceReferenceMacro();
-  if (!macro)
-  {
-    return EC_MemoryExhausted;
-  }
-  OFCondition result = macro->setReferencedSOPClassUID(sopClassUID);
-  if (result.good()) result = macro->setReferencedSOPInstanceUID(sopInstanceUID);
-  if (result.good())
-  {
-    m_ReferencedInstanceSequence.push_back(macro);
-  }
-  else
-  {
-    delete macro;
-    result = IOD_EC_InvalidElementValue;
-  }
-  return result;
+    return result;
 }
 
-
 // ---------------------- SOPInstanceReferenceMacro ----------------------
 
-
-SOPInstanceReferenceMacro::SOPInstanceReferenceMacro(OFshared_ptr< DcmItem > item,
-                                                     OFshared_ptr< IODRules > rules,
+SOPInstanceReferenceMacro::SOPInstanceReferenceMacro(OFshared_ptr<DcmItem> item,
+                                                     OFshared_ptr<IODRules> rules,
                                                      IODComponent* parent)
-: IODComponent(item, rules, parent)
+    : IODComponent(item, rules, parent)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 SOPInstanceReferenceMacro::SOPInstanceReferenceMacro(IODComponent* parent)
-: IODComponent(parent)
+    : IODComponent(parent)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 SOPInstanceReferenceMacro::~SOPInstanceReferenceMacro()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
 OFString SOPInstanceReferenceMacro::getName() const
 {
-  return "SOPInstanceReferenceMacro";
+    return "SOPInstanceReferenceMacro";
 }
 
-
 void SOPInstanceReferenceMacro::resetRules()
 {
-  // Parameters for Rule are tag, VM, type (1,1C,2,2C,3), module name and logical IOD level
-  m_Rules->addRule(new IODRule(DCM_ReferencedSOPClassUID, "1", "1", getName(), DcmIODTypes::IE_UNDEFINED), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ReferencedSOPInstanceUID, "1", "1",  getName(), DcmIODTypes::IE_UNDEFINED), OFTrue);
+    // Parameters for Rule are tag, VM, type (1,1C,2,2C,3), module name and logical IOD level
+    m_Rules->addRule(new IODRule(DCM_ReferencedSOPClassUID, "1", "1", getName(), DcmIODTypes::IE_UNDEFINED), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ReferencedSOPInstanceUID, "1", "1", getName(), DcmIODTypes::IE_UNDEFINED), OFTrue);
 }
 
-
 // -- get dicom attributes --
 
-OFCondition SOPInstanceReferenceMacro::getReferencedSOPClassUID(OFString &value,
-                                                                const signed long pos)
+OFCondition SOPInstanceReferenceMacro::getReferencedSOPClassUID(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_ReferencedSOPClassUID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_ReferencedSOPClassUID, *m_Item, value, pos);
 }
 
-OFCondition SOPInstanceReferenceMacro::getReferencedSOPInstanceUID(OFString &value,
-                                                                   const signed long pos)
+OFCondition SOPInstanceReferenceMacro::getReferencedSOPInstanceUID(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_ReferencedSOPInstanceUID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_ReferencedSOPInstanceUID, *m_Item, value, pos);
 }
 
 // -- set dicom attributes --
 
-OFCondition SOPInstanceReferenceMacro::setReferencedSOPClassUID(const OFString& value,
-                                                                const OFBool checkValue)
+OFCondition SOPInstanceReferenceMacro::setReferencedSOPClassUID(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_ReferencedSOPClassUID, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_ReferencedSOPClassUID, value);
+    return result;
 }
 
-
-OFCondition SOPInstanceReferenceMacro::setReferencedSOPInstanceUID(const OFString& value,
-                                                                   const OFBool checkValue)
+OFCondition SOPInstanceReferenceMacro::setReferencedSOPInstanceUID(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_ReferencedSOPInstanceUID, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_ReferencedSOPInstanceUID, value);
+    return result;
 }
 
-
 // ---------------------- ImageSOPInstanceReferenceMacro ----------------------
 
-
 ImageSOPInstanceReferenceMacro::ImageSOPInstanceReferenceMacro()
-  : ReferencedFrameNumber(DCM_ReferencedFrameNumber),
-    ReferencedSegmentNumber(DCM_ReferencedSegmentNumber)
+    : ReferencedFrameNumber(DCM_ReferencedFrameNumber)
+    ReferencedSegmentNumber(DCM_ReferencedSegmentNumber)
 {
-
 }
 
-
 OFCondition ImageSOPInstanceReferenceMacro::create(const OFString& sopClassUID,
                                                    const OFString& sopInstanceUID,
                                                    ImageSOPInstanceReferenceMacro*& result)
 {
-  result = new ImageSOPInstanceReferenceMacro();
-  if (!result)
-    return EC_MemoryExhausted;
+    result = new ImageSOPInstanceReferenceMacro();
+    if (!result)
+        return EC_MemoryExhausted;
 
-  OFCondition cond = result->setReferencedSOPClassUID(sopClassUID);
-  if (cond.good())
-  {
-    cond = result->setReferencedSOPInstanceUID(sopInstanceUID);
-  }
-  if (cond.bad())
-  {
-    delete result;
-    result = NULL;
-  }
-  return cond;
+    OFCondition cond = result->setReferencedSOPClassUID(sopClassUID);
+    if (cond.good())
+    {
+        cond = result->setReferencedSOPInstanceUID(sopInstanceUID);
+    }
+    if (cond.bad())
+    {
+        delete result;
+        result = NULL;
+    }
+    return cond;
 }
 
-
 OFCondition ImageSOPInstanceReferenceMacro::create(const OFString& sopClassUID,
                                                    const OFString& sopInstanceUID,
-                                                   const OFVector< Uint16 >& refFramesOrSegments,
+                                                   const OFVector<Uint16>& refFramesOrSegments,
                                                    ImageSOPInstanceReferenceMacro*& result)
 {
-  OFCondition cond = create(sopClassUID, sopInstanceUID, result);
-  if (cond.good())
-  {
-    if (!refFramesOrSegments.empty())
+    OFCondition cond = create(sopClassUID, sopInstanceUID, result);
+    if (cond.good())
     {
-      if (sopClassUID == UID_SegmentationStorage)
-      {
-        cond = result->setReferencedSegmentNumber(refFramesOrSegments);
-      }
-      else
-      {
-        cond = result->setReferencedFrameNumber(refFramesOrSegments);
-      }
-    }
-    if (cond.bad())
-    {
-      delete result;
-      result = NULL;
+        if (!refFramesOrSegments.empty())
+        {
+            if (sopClassUID == UID_SegmentationStorage)
+            {
+                cond = result->setReferencedSegmentNumber(refFramesOrSegments);
+            }
+            else
+            {
+                cond = result->setReferencedFrameNumber(refFramesOrSegments);
+            }
+        }
+        if (cond.bad())
+        {
+            delete result;
+            result = NULL;
+        }
     }
-  }
-  return cond;
+    return cond;
 }
 
-
 ImageSOPInstanceReferenceMacro::~ImageSOPInstanceReferenceMacro()
 {
 }
 
 int ImageSOPInstanceReferenceMacro::compare(const IODComponent& rhs) const
 {
-  const ImageSOPInstanceReferenceMacro *macro = OFstatic_cast(const ImageSOPInstanceReferenceMacro*, &rhs);
-  if (macro == NULL) return -1;
-  int result = ReferencedFrameNumber.compare(macro->ReferencedFrameNumber);
-  if (result == 0) ReferencedSegmentNumber.compare(macro->ReferencedSegmentNumber);
-  if (result == 0) return SOPInstanceReferenceMacro::compare(rhs);
-  return result;
+    const ImageSOPInstanceReferenceMacro* macro = OFstatic_cast(const ImageSOPInstanceReferenceMacro*, &rhs);
+    if (macro == NULL)
+        return -1;
+    int result = ReferencedFrameNumber.compare(macro->ReferencedFrameNumber);
+    if (result == 0)
+        ReferencedSegmentNumber.compare(macro->ReferencedSegmentNumber);
+    if (result == 0)
+        return SOPInstanceReferenceMacro::compare(rhs);
+    return result;
 }
 
 void ImageSOPInstanceReferenceMacro::clear()
 {
-  SOPInstanceReferenceMacro::clearData();
-  ReferencedFrameNumber.clear();
-  ReferencedSegmentNumber.clear();
+    SOPInstanceReferenceMacro::clearData();
+    ReferencedFrameNumber.clear();
+    ReferencedSegmentNumber.clear();
 }
 
-
-OFCondition ImageSOPInstanceReferenceMacro::read(DcmItem& source,
-                                                 const OFBool clearOldData)
+OFCondition ImageSOPInstanceReferenceMacro::read(DcmItem& source, const OFBool clearOldData)
 {
-  /* re-initialize object */
-  if (clearOldData)
-    clear();
+    /* re-initialize object */
+    if (clearOldData)
+        clear();
 
-  OFCondition result = SOPInstanceReferenceMacro::read(source, clearOldData);
+    OFCondition result = SOPInstanceReferenceMacro::read(source, clearOldData);
 
-  DcmIODUtil::getAndCheckElementFromDataset(source, ReferencedFrameNumber, "1-n", "1C", "ImageSOPInstanceReferenceMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(source, ReferencedSegmentNumber, "1-n", "1C", "ImageSOPInstanceReferenceMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(
+        source, ReferencedFrameNumber, "1-n", "1C", "ImageSOPInstanceReferenceMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(
+        source, ReferencedSegmentNumber, "1-n", "1C", "ImageSOPInstanceReferenceMacro");
 
-  return result;
+    return result;
 }
 
-
 OFCondition ImageSOPInstanceReferenceMacro::write(DcmItem& item)
 {
-  OFCondition result = EC_Normal;
-  /* copy all elements to dataset */
-  DcmIODUtil::copyElementToDataset(result, item, ReferencedFrameNumber, "1-n" /* VM */, "1C" /* Type */, "ImageSOPInstanceReferenceMacro");
-  DcmIODUtil::copyElementToDataset(result, item, ReferencedSegmentNumber, "1-n", "1C", "ImageSOPInstanceReferenceMacro");
+    OFCondition result = EC_Normal;
+    /* copy all elements to dataset */
+    DcmIODUtil::copyElementToDataset(
+        result, item, ReferencedFrameNumber, "1-n" /* VM */, "1C" /* Type */, "ImageSOPInstanceReferenceMacro");
+    DcmIODUtil::copyElementToDataset(
+        result, item, ReferencedSegmentNumber, "1-n", "1C", "ImageSOPInstanceReferenceMacro");
 
-  if ( result.good() )
-    result = SOPInstanceReferenceMacro::write(item);
+    if (result.good())
+        result = SOPInstanceReferenceMacro::write(item);
 
-  return result;
+    return result;
 }
 
 // -- get dicom attributes --
 
-OFCondition ImageSOPInstanceReferenceMacro::getReferencedFrameNumber(OFVector<Uint16> &values)
+OFCondition ImageSOPInstanceReferenceMacro::getReferencedFrameNumber(OFVector<Uint16>values)
 {
-  // cast away const since underlying dcmdata routine is not const...
-  DcmIntegerString *is = OFconst_cast(DcmIntegerString*, &ReferencedFrameNumber);
-  for (size_t n = 0; n < is->getNumberOfValues(); n++)
-  {
-    Sint32 sint = 0;
-    is->getSint32(sint, OFstatic_cast(unsigned long, n));
-    if (sint < 0)
+    // cast away const since underlying dcmdata routine is not const...
+    DcmIntegerString* is = OFconst_cast(DcmIntegerString*, &ReferencedFrameNumber);
+    for (size_t n = 0; n < is->getNumberOfValues(); n++)
     {
-      DCMIOD_WARN("Invalid Referenced Frame Number in Image SOP Instance Reference Macro: " << sint);
-      return EC_CorruptedData;
+        Sint32 sint = 0;
+        is->getSint32(sint, OFstatic_cast(unsigned long, n));
+        if (sint < 0)
+        {
+            DCMIOD_WARN("Invalid Referenced Frame Number in Image SOP Instance Reference Macro: " << sint);
+            return EC_CorruptedData;
+        }
+        values.push_back(OFstatic_cast(Uint16, sint));
     }
-    values.push_back(OFstatic_cast(Uint16, sint));
-  }
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
-OFCondition ImageSOPInstanceReferenceMacro::getReferencedSegmentNumber(OFVector<Uint16> &values)
+OFCondition ImageSOPInstanceReferenceMacro::getReferencedSegmentNumber(OFVector<Uint16>& values)
 {
-  // cast away const since underlying dcmdata routine is not const...
-  DcmUnsignedShort *us = OFconst_cast(DcmUnsignedShort*, &ReferencedSegmentNumber);
-  return DcmIODUtil::getUint16ValuesFromElement(*us, values);
+    // cast away const since underlying dcmdata routine is not const...
+    DcmUnsignedShort* us = OFconst_cast(DcmUnsignedShort*, &ReferencedSegmentNumber);
+    return DcmIODUtil::getUint16ValuesFromElement(*us, values);
 }
 
 // -- set dicom attributes --
 
-
 OFCondition ImageSOPInstanceReferenceMacro::setReferencedFrameNumber(const OFVector<Uint16>& values,
                                                                      const OFBool checkValue)
 {
-  return DcmIODUtil::setUint16ValuesOnElement(ReferencedFrameNumber, values, "1-n", checkValue);
+    return DcmIODUtil::setUint16ValuesOnElement(ReferencedFrameNumber, values, "1-n", checkValue);
 }
 
-
-OFCondition ImageSOPInstanceReferenceMacro::addReferencedFrameNumber(const Uint16& value,
-                                                                     const OFBool checkValue)
+OFCondition ImageSOPInstanceReferenceMacro::addReferencedFrameNumber(const Uint16& value, const OFBool checkValue)
 {
-  (void)checkValue;
-  OFString val;
-  ReferencedFrameNumber.getOFStringArray(val);
-  if (ReferencedFrameNumber.getNumberOfValues() > 0)
-  {
-    val += "\\";
-  }
-  char buf[10];
-  sprintf(buf, "%u", value);
-  val += buf;
-  return ReferencedFrameNumber.putOFStringArray(val);
+    (void)checkValue;
+    OFString val;
+    ReferencedFrameNumber.getOFStringArray(val);
+    if (ReferencedFrameNumber.getNumberOfValues() > 0)
+    {
+        val += "\\";
+    }
+    char buf[10];
+    sprintf(buf, "%u", value);
+    val += buf;
+    return ReferencedFrameNumber.putOFStringArray(val);
 }
 
-
-
 OFCondition ImageSOPInstanceReferenceMacro::setReferencedSegmentNumber(const OFVector<Uint16>& values,
                                                                        const OFBool checkValue)
 {
-  return DcmIODUtil::setUint16ValuesOnElement(ReferencedSegmentNumber, values, "1-n", checkValue);
+    return DcmIODUtil::setUint16ValuesOnElement(ReferencedSegmentNumber, values, "1-n", checkValue);
 }
 
-
-OFCondition ImageSOPInstanceReferenceMacro::addReferencedSegmentNumber(const Uint16& value,
-                                                                       const OFBool checkValue)
+OFCondition ImageSOPInstanceReferenceMacro::addReferencedSegmentNumber(const Uint16& value, const OFBool checkValue)
 {
-  (void)checkValue;
-  const unsigned long count = ReferencedSegmentNumber.getNumberOfValues();
-  return ReferencedSegmentNumber.putUint16(value, count /* starts with 0, so add new value at the end */);
-
+    (void)checkValue;
+    const unsigned long count = ReferencedSegmentNumber.getNumberOfValues();
+    return ReferencedSegmentNumber.putUint16(value, count /* starts with 0, so add new value at the end */);
 }
 
-
 // ---------------------- GeneralAnatomyMacro ----------------------
 
-
-GeneralAnatomyMacro::GeneralAnatomyMacro(const OFString& type) :
-  m_Type(type),
-  m_AnatomicRegion(),
-  m_AnatomicRegionModifier(),
-  m_PrimaryAnatomicStructure("3" /* Modifier in Primary Anatomic Structure is always optional */, "1", DCM_PrimaryAnatomicStructureModifierSequence)
+GeneralAnatomyMacro::GeneralAnatomyMacro(const OFString& type)
+    : m_Type(type)
+    , m_AnatomicRegion()
+    , m_AnatomicRegionModifier()
+    , m_PrimaryAnatomicStructure("3" /* Modifier in Primary Anatomic Structure is always optional */,
+                                 "1",
+                                 DCM_PrimaryAnatomicStructureModifierSequence)
 {
-  m_Type = type;
+    m_Type = type;
 }
 
-
 GeneralAnatomyMacro::GeneralAnatomyMacro(const GeneralAnatomyMacro& rhs)
-:  m_Type(rhs.m_Type),
-   m_AnatomicRegion(),
-   m_AnatomicRegionModifier(),
-   m_PrimaryAnatomicStructure("3" /* Modifier in Primary Anatomic Structure is always optional */, "1", DCM_PrimaryAnatomicStructureModifierSequence)
+    : m_Type(rhs.m_Type)
+    , m_AnatomicRegion()
+    , m_AnatomicRegionModifier()
+    , m_PrimaryAnatomicStructure("3" /* Modifier in Primary Anatomic Structure is always optional */,
+                                 "1",
+                                 DCM_PrimaryAnatomicStructureModifierSequence)
 {
-  *this = rhs;
+    *this = rhs;
 }
 
-
 GeneralAnatomyMacro& GeneralAnatomyMacro::operator=(const GeneralAnatomyMacro& rhs)
 {
-  if (this != &rhs)
-  {
-    clearData();
-    m_Type = rhs.m_Type;
-    m_AnatomicRegion = rhs.m_AnatomicRegion;
-    m_PrimaryAnatomicStructure = rhs.m_PrimaryAnatomicStructure;
-
-    OFVector<CodeSequenceMacro*>::const_iterator it = rhs.m_AnatomicRegionModifier.begin();
-    while ( it != rhs.m_AnatomicRegionModifier.end() )
+    if (this != &rhs)
     {
-      m_AnatomicRegionModifier.push_back( new CodeSequenceMacro(**it) );
-      it++;
+        clearData();
+        m_Type                     = rhs.m_Type;
+        m_AnatomicRegion           = rhs.m_AnatomicRegion;
+        m_PrimaryAnatomicStructure = rhs.m_PrimaryAnatomicStructure;
+
+        OFVector<CodeSequenceMacro*>::const_iterator it = rhs.m_AnatomicRegionModifier.begin();
+        while (it != rhs.m_AnatomicRegionModifier.end())
+        {
+            m_AnatomicRegionModifier.push_back(new CodeSequenceMacro(**it));
+            it++;
+        }
     }
-  }
-  return *this;
+    return *this;
 }
 
-
 GeneralAnatomyMacro::~GeneralAnatomyMacro()
 {
-  clearData();
+    clearData();
 }
 
-
 void GeneralAnatomyMacro::clearData()
 {
-  // m_Type stays the same
-  m_AnatomicRegion.clearData();
-  DcmIODUtil::freeContainer(m_AnatomicRegionModifier);
-  m_PrimaryAnatomicStructure.clearData();
+    // m_Type stays the same
+    m_AnatomicRegion.clearData();
+    DcmIODUtil::freeContainer(m_AnatomicRegionModifier);
+    m_PrimaryAnatomicStructure.clearData();
 }
 
-
 OFCondition GeneralAnatomyMacro::check(const OFBool quiet)
 {
-  OFCondition result = m_AnatomicRegion.check(quiet);
-  if (result.bad())
-    return result;
+    OFCondition result = m_AnatomicRegion.check(quiet);
+    if (result.bad())
+        return result;
 
-  OFVector<CodeSequenceMacro*>::iterator it = m_AnatomicRegionModifier.begin();
-  while (it != m_AnatomicRegionModifier.begin())
-  {
-    result = (*it)->check(quiet);
-    if (result.bad()) return result;
-    it++;
-  }
-  // Primary Anatomic Structure is optional (type 3), so only check if
-  // user intended to fill in something.
-  if (!m_PrimaryAnatomicStructure.empty())
-  {
-    result = m_PrimaryAnatomicStructure.check(quiet);
-  }
-  return result;
+    OFVector<CodeSequenceMacro*>::iterator it = m_AnatomicRegionModifier.begin();
+    while (it != m_AnatomicRegionModifier.begin())
+    {
+        result = (*it)->check(quiet);
+        if (result.bad())
+            return result;
+        it++;
+    }
+    // Primary Anatomic Structure is optional (type 3), so only check if
+    // user intended to fill in something.
+    if (!m_PrimaryAnatomicStructure.empty())
+    {
+        result = m_PrimaryAnatomicStructure.check(quiet);
+    }
+    return result;
 }
 
-
 CodeSequenceMacro& GeneralAnatomyMacro::getAnatomicRegion()
 {
-  return m_AnatomicRegion;
+    return m_AnatomicRegion;
 }
 
-
 OFVector<CodeSequenceMacro*>& GeneralAnatomyMacro::getAnatomicRegionModifier()
 {
-  return m_AnatomicRegionModifier;
+    return m_AnatomicRegionModifier;
 }
 
-
 PrimaryAnatomicStructureMacro& GeneralAnatomyMacro::getPrimaryAnatomicStructure()
 {
-  return m_PrimaryAnatomicStructure;
+    return m_PrimaryAnatomicStructure;
 }
 
-
 // Reads Anatomic Region Sequence and Primary Anatomic Structure Macro from given item
-OFCondition GeneralAnatomyMacro::read(DcmItem& source,
-                                      const OFBool clearOldData)
+OFCondition GeneralAnatomyMacro::read(DcmItem& source, const OFBool clearOldData)
 {
-  OFCondition result = EC_Normal;
+    OFCondition result = EC_Normal;
 
-  /* re-initialize object */
-  if (clearOldData)
-    clearData();
+    /* re-initialize object */
+    if (clearOldData)
+        clearData();
 
-  /* read Anatomic Region Sequence item into Code Sequence Macro */
-  DcmIODUtil::readSingleItem<CodeSequenceMacro>(source, DCM_AnatomicRegionSequence, m_AnatomicRegion, m_Type, "GeneralAnatomyMacro");
+    /* read Anatomic Region Sequence item into Code Sequence Macro */
+    DcmIODUtil::readSingleItem<CodeSequenceMacro>(
+        source, DCM_AnatomicRegionSequence, m_AnatomicRegion, m_Type, "GeneralAnatomyMacro");
 
-  /* read Primary Anatomic Structure Macro (main level, i.e.\ original item) */
-  DcmIODUtil::readSingleItem(source, DCM_PrimaryAnatomicStructureSequence, m_PrimaryAnatomicStructure, "3", "GeneralAnatomyMacro");
+    /* read Primary Anatomic Structure Macro (main level, i.e.\ original item) */
+    DcmIODUtil::readSingleItem(
+        source, DCM_PrimaryAnatomicStructureSequence, m_PrimaryAnatomicStructure, "3", "GeneralAnatomyMacro");
 
-  /* Get the single item from Anatomic Region Sequence and read modifier if found */
-  DcmItem* localItem = NULL;
-  if ( source.findAndGetSequenceItem(DCM_AnatomicRegionSequence, localItem).bad() )
-  {
-    return result;
-  }
+    /* Get the single item from Anatomic Region Sequence and read modifier if found */
+    DcmItem* localItem = NULL;
+    if (source.findAndGetSequenceItem(DCM_AnatomicRegionSequence, localItem).bad())
+    {
+        return result;
+    }
 
-  /* read Anatomic Region Modifier Sequence from */
-  DcmIODUtil::readSubSequence<OFVector<CodeSequenceMacro*> >
-  ( *localItem, /* item of Anatomic Region Sequence */
-    DCM_AnatomicRegionModifierSequence,
-    m_AnatomicRegionModifier,
-    "1-n",
-    "3",
-    "GeneralAnatomyMacro" );
+    /* read Anatomic Region Modifier Sequence from */
+    DcmIODUtil::readSubSequence<OFVector<CodeSequenceMacro*> >(*localItem, /* item of Anatomic Region Sequence */
+                                                               DCM_AnatomicRegionModifierSequence,
+                                                               m_AnatomicRegionModifier,
+                                                               "1-n",
+                                                               "3",
+                                                               "GeneralAnatomyMacro");
 
-  return result;
+    return result;
 }
 
-
 /// Write Anatomic Region Sequence from given item
 OFCondition GeneralAnatomyMacro::write(DcmItem& item)
 {
-  OFCondition result = EC_Normal;
+    OFCondition result = EC_Normal;
 
-  /* delete old data */
-  item.findAndDeleteElement(DCM_AnatomicRegionSequence);
-  item.findAndDeleteElement(DCM_PrimaryAnatomicStructureSequence);
+    /* delete old data */
+    item.findAndDeleteElement(DCM_AnatomicRegionSequence);
+    item.findAndDeleteElement(DCM_PrimaryAnatomicStructureSequence);
 
-  /* Write sub structures */
-  DcmIODUtil::writeSingleItem<CodeSequenceMacro>(result, DCM_AnatomicRegionSequence, m_AnatomicRegion, item, m_Type, "GeneralAnatomyMacro");
-  if (result.good())
-  {
-    DcmItem* seqItem = NULL;
-    result = item.findAndGetSequenceItem(DCM_AnatomicRegionSequence, seqItem, 0);
+    /* Write sub structures */
+    DcmIODUtil::writeSingleItem<CodeSequenceMacro>(
+        result, DCM_AnatomicRegionSequence, m_AnatomicRegion, item, m_Type, "GeneralAnatomyMacro");
     if (result.good())
     {
-      DcmIODUtil::writeSubSequence<OFVector<CodeSequenceMacro*> >
-      ( result,
-        DCM_AnatomicRegionModifierSequence,
-        m_AnatomicRegionModifier,
-        *seqItem,
-        "1-n",
-        "3",
-        "GeneralAnatomyMacro");
+        DcmItem* seqItem = NULL;
+        result           = item.findAndGetSequenceItem(DCM_AnatomicRegionSequence, seqItem, 0);
+        if (result.good())
+        {
+            DcmIODUtil::writeSubSequence<OFVector<CodeSequenceMacro*> >(result,
+                                                                        DCM_AnatomicRegionModifierSequence,
+                                                                        m_AnatomicRegionModifier,
+                                                                        *seqItem,
+                                                                        "1-n",
+                                                                        "3",
+                                                                        "GeneralAnatomyMacro");
+        }
     }
-  }
-  DcmIODUtil::writeSingleItem(result, DCM_PrimaryAnatomicStructureSequence, m_PrimaryAnatomicStructure, item, "3", "GeneralAnatomyMacro");
-  return result;
+    DcmIODUtil::writeSingleItem(
+        result, DCM_PrimaryAnatomicStructureSequence, m_PrimaryAnatomicStructure, item, "3", "GeneralAnatomyMacro");
+    return result;
 }
 
-
 int GeneralAnatomyMacro::compare(const GeneralAnatomyMacro& rhs) const
 {
-  int result = m_AnatomicRegion.compare(rhs.m_AnatomicRegion);
-  if (result == 0)
-  {
-    if (m_AnatomicRegionModifier.size() > rhs.m_AnatomicRegionModifier.size())
+    int result = m_AnatomicRegion.compare(rhs.m_AnatomicRegion);
+    if (result == 0)
     {
-      return 1;
-    }
-    else if (m_AnatomicRegionModifier.size() < rhs.m_AnatomicRegionModifier.size())
-    {
-      return -1;
-    }
+        if (m_AnatomicRegionModifier.size() > rhs.m_AnatomicRegionModifier.size())
+        {
+            return 1;
+        }
+        else if (m_AnatomicRegionModifier.size() < rhs.m_AnatomicRegionModifier.size())
+        {
+            return -1;
+        }
 
-    for (size_t m = 0; m < m_AnatomicRegionModifier.size(); m++)
-    {
-      rhs.m_AnatomicRegionModifier[m];
-      result = m_AnatomicRegionModifier[m]->compare(  *(rhs.m_AnatomicRegionModifier[m]) );
-      if (result != 0)
-      {
-        return result;
-      }
+        for (size_t m = 0; m < m_AnatomicRegionModifier.size(); m++)
+        {
+            result = m_AnatomicRegionModifier[m]->compare(*(rhs.m_AnatomicRegionModifier[m]));
+            if (result != 0)
+            {
+                return result;
+            }
+        }
+        result = m_PrimaryAnatomicStructure.compare(rhs.m_PrimaryAnatomicStructure);
     }
-    result = m_PrimaryAnatomicStructure.compare(rhs.m_PrimaryAnatomicStructure);
-  }
-  return result;
+    return result;
 }
 
-
 // ---------------------- AlgorithmIdentificationMacro ----------------------
 
-
-AlgorithmIdentificationMacro::AlgorithmIdentificationMacro() :
-  m_AlgorithmFamilyCode(),
-  m_AlgorithmNameCode(),
-  m_AlgorithmName(DCM_AlgorithmName),
-  m_AlgorithmVersion(DCM_AlgorithmVersion),
-  m_AlgorithmParameters(DCM_AlgorithmParameters),
-  m_AlgorithmSource(DCM_AlgorithmSource)
+AlgorithmIdentificationMacro::AlgorithmIdentificationMacro()
+    : m_AlgorithmFamilyCode()
+    , m_AlgorithmNameCode()
+    , m_AlgorithmName(DCM_AlgorithmName)
+    , m_AlgorithmVersion(DCM_AlgorithmVersion)
+    , m_AlgorithmParameters(DCM_AlgorithmParameters)
+    , m_AlgorithmSource(DCM_AlgorithmSource)
 {
-
 }
 //
 AlgorithmIdentificationMacro::~AlgorithmIdentificationMacro()
 {
-  clearData();
+    clearData();
 }
 
-
 void AlgorithmIdentificationMacro::clearData()
 {
-  m_AlgorithmFamilyCode.clearData();
-  m_AlgorithmNameCode.clearData();
-  m_AlgorithmName.clear();
-  m_AlgorithmVersion.clear();
-  m_AlgorithmParameters.clear();
-  m_AlgorithmSource.clear();
+    m_AlgorithmFamilyCode.clearData();
+    m_AlgorithmNameCode.clearData();
+    m_AlgorithmName.clear();
+    m_AlgorithmVersion.clear();
+    m_AlgorithmParameters.clear();
+    m_AlgorithmSource.clear();
 }
 
-
 OFCondition AlgorithmIdentificationMacro::check(const OFBool quiet)
 {
-  OFCondition result;
-  result = m_AlgorithmFamilyCode.check(quiet);
-  if ( result.good() )
-  {
-    if ( m_AlgorithmName.isEmpty() || m_AlgorithmVersion.isEmpty() )
+    OFCondition result;
+    result = m_AlgorithmFamilyCode.check(quiet);
+    if (result.good())
     {
-      result = EC_MissingValue;
+        if (m_AlgorithmName.isEmpty() || m_AlgorithmVersion.isEmpty())
+        {
+            result = EC_MissingValue;
+        }
     }
-  }
-  return result;
+    return result;
 }
 
-
-
 CodeSequenceMacro& AlgorithmIdentificationMacro::getAlgorithmFamilyCode()
 {
-  return m_AlgorithmFamilyCode;
+    return m_AlgorithmFamilyCode;
 }
 
-
 CodeSequenceMacro& AlgorithmIdentificationMacro::getAlgorithmNameCode()
 {
-  return m_AlgorithmNameCode;
+    return m_AlgorithmNameCode;
 }
 
-
-OFCondition AlgorithmIdentificationMacro::getAlgorithmName(OFString& value,
-                                                           const signed long pos)
+OFCondition AlgorithmIdentificationMacro::getAlgorithmName(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_AlgorithmName, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_AlgorithmName, value, pos);
 }
 
-
-OFCondition AlgorithmIdentificationMacro::getAlgorithmVersion(OFString& value,
-                                                              const signed long pos)
+OFCondition AlgorithmIdentificationMacro::getAlgorithmVersion(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_AlgorithmVersion, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_AlgorithmVersion, value, pos);
 }
 
-
-OFCondition AlgorithmIdentificationMacro::getAlgorithmParameters(OFString& value,
-                                                                 const signed long pos)
+OFCondition AlgorithmIdentificationMacro::getAlgorithmParameters(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_AlgorithmParameters, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_AlgorithmParameters, value, pos);
 }
 
-
-OFCondition AlgorithmIdentificationMacro::getAlgorithmSource(OFString& value,
-                                                             const signed long pos)
+OFCondition AlgorithmIdentificationMacro::getAlgorithmSource(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_AlgorithmSource, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_AlgorithmSource, value, pos);
 }
 
-
-OFCondition AlgorithmIdentificationMacro::setAlgorithmName(const OFString& value,
-                                                           const OFBool checkValue)
+OFCondition AlgorithmIdentificationMacro::setAlgorithmName(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_AlgorithmName.putOFStringArray(value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_AlgorithmName.putOFStringArray(value);
+    return result;
 }
 
-
-OFCondition AlgorithmIdentificationMacro::setAlgorithmVersion(const OFString& value,
-                                                              const OFBool checkValue)
+OFCondition AlgorithmIdentificationMacro::setAlgorithmVersion(const OFString& value, const OFBool checkValue)
 
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_AlgorithmVersion.putOFStringArray(value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_AlgorithmVersion.putOFStringArray(value);
+    return result;
 }
 
-
-OFCondition AlgorithmIdentificationMacro::setAlgorithmParameters(const OFString& value,
-                                                                 const OFBool checkValue)
+OFCondition AlgorithmIdentificationMacro::setAlgorithmParameters(const OFString& value, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_AlgorithmParameters.putOFStringArray(value);
+    (void)checkValue;
+    return m_AlgorithmParameters.putOFStringArray(value);
 }
 
-
-OFCondition AlgorithmIdentificationMacro::setAlgorithmSource(const OFString& value,
-                                                             const OFBool checkValue)
+OFCondition AlgorithmIdentificationMacro::setAlgorithmSource(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_AlgorithmSource.putOFStringArray(value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_AlgorithmSource.putOFStringArray(value);
+    return result;
 }
 
-
 /// Reads Anatomic Region Sequence and Primary Anatomic Structure Macro from given item
-OFCondition AlgorithmIdentificationMacro::read(DcmItem& source,
-                                               const OFBool clearOldData)
+OFCondition AlgorithmIdentificationMacro::read(DcmItem& source, const OFBool clearOldData)
 {
-  OFCondition result;
+    OFCondition result;
 
-  if (clearOldData)
-    clearData();
+    if (clearOldData)
+        clearData();
 
-  DcmIODUtil::readSingleItem<CodeSequenceMacro>
-  (
-    source,
-    DCM_AlgorithmFamilyCodeSequence,
-    m_AlgorithmFamilyCode,
-    "1",
-    "AlgorithmIdentificationMacro"
-  );
+    DcmIODUtil::readSingleItem<CodeSequenceMacro>(
+        source, DCM_AlgorithmFamilyCodeSequence, m_AlgorithmFamilyCode, "1", "AlgorithmIdentificationMacro");
 
-  DcmIODUtil::readSingleItem<CodeSequenceMacro>
-  (
-    source,
-    DCM_AlgorithmNameCodeSequence,
-    m_AlgorithmNameCode,
-    "3",
-    "AlgorithmIdentificationMacro");
+    DcmIODUtil::readSingleItem<CodeSequenceMacro>(
+        source, DCM_AlgorithmNameCodeSequence, m_AlgorithmNameCode, "3", "AlgorithmIdentificationMacro");
 
-  DcmIODUtil::getAndCheckElementFromDataset(source, m_AlgorithmName, "1", "1", "AlgorithmIdentificationMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(source, m_AlgorithmVersion, "1", "1", "AlgorithmIdentificationMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(source, m_AlgorithmParameters, "1", "3", "AlgorithmIdentificationMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(source, m_AlgorithmSource, "1", "3", "AlgorithmIdentificationMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(source, m_AlgorithmName, "1", "1", "AlgorithmIdentificationMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(source, m_AlgorithmVersion, "1", "1", "AlgorithmIdentificationMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(source, m_AlgorithmParameters, "1", "3", "AlgorithmIdentificationMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(source, m_AlgorithmSource, "1", "3", "AlgorithmIdentificationMacro");
 
-  return result;
+    return result;
 }
 
-
 OFCondition AlgorithmIdentificationMacro::write(DcmItem& item)
 {
-  OFCondition result = EC_Normal;
+    OFCondition result = EC_Normal;
 
-  // write to item
-  DcmIODUtil::copyElementToDataset(result, item, m_AlgorithmName, "1", "1", "AlgorithmIdentificationMacro");
-  DcmIODUtil::copyElementToDataset(result, item, m_AlgorithmVersion, "1", "1", "AlgorithmIdentificationMacro");
-  DcmIODUtil::copyElementToDataset(result, item, m_AlgorithmParameters, "1", "3", "AlgorithmIdentificationMacro");
-  DcmIODUtil::copyElementToDataset(result, item, m_AlgorithmSource, "1", "3", "AlgorithmIdentificationMacro");
+    // write to item
+    DcmIODUtil::copyElementToDataset(result, item, m_AlgorithmName, "1", "1", "AlgorithmIdentificationMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_AlgorithmVersion, "1", "1", "AlgorithmIdentificationMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_AlgorithmParameters, "1", "3", "AlgorithmIdentificationMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_AlgorithmSource, "1", "3", "AlgorithmIdentificationMacro");
 
-  DcmIODUtil::writeSingleItem<CodeSequenceMacro>
-  (  result,
-     DCM_AlgorithmFamilyCodeSequence,
-     m_AlgorithmFamilyCode,
-     item,
-     "1",
-     "AlgorithmIdentificationMacro"
-  );
+    DcmIODUtil::writeSingleItem<CodeSequenceMacro>(
+        result, DCM_AlgorithmFamilyCodeSequence, m_AlgorithmFamilyCode, item, "1", "AlgorithmIdentificationMacro");
 
-  DcmIODUtil::writeSingleItem<CodeSequenceMacro>
-  (  result,
-     DCM_AlgorithmNameCodeSequence,
-     m_AlgorithmNameCode,
-     item,
-     "3",
-     "AlgorithmIdentificationMacro"
-  );
+    DcmIODUtil::writeSingleItem<CodeSequenceMacro>(
+        result, DCM_AlgorithmNameCodeSequence, m_AlgorithmNameCode, item, "3", "AlgorithmIdentificationMacro");
 
-  return result;
+    return result;
 }
 
-
 // ---------------------- ContentIdentificationMacro ----------------------
 
-ContentIdentificationMacro::ContentIdentificationMacro() :
-  m_InstanceNumber(DCM_InstanceNumber),
-  m_ContentLabel(DCM_ContentLabel),
-  m_ContentDescription(DCM_ContentDescription),
-  m_AlternateContentDescription(),
-  m_ContentCreatorName(DCM_ContentCreatorName),
-  m_ContentCreatorIdentificationCode(),
-  m_IODRules()
+ContentIdentificationMacro::ContentIdentificationMacro()
+    : m_InstanceNumber(DCM_InstanceNumber)
+    , m_ContentLabel(DCM_ContentLabel)
+    , m_ContentDescription(DCM_ContentDescription)
+    , m_AlternateContentDescription()
+    , m_ContentCreatorName(DCM_ContentCreatorName)
+    , m_ContentCreatorIdentificationCode()
+    , m_IODRules()
 {
-  resetRules();
+    resetRules();
 }
 
-
 ContentIdentificationMacro::ContentIdentificationMacro(const OFString& instanceNumber,
                                                        const OFString& contentLabel,
                                                        const OFString& contentDescription,
-                                                       const OFString& contentCreatorName) :
-  m_InstanceNumber(DCM_InstanceNumber),
-  m_ContentLabel(DCM_ContentLabel),
-  m_ContentDescription(DCM_ContentDescription),
-  m_AlternateContentDescription(),
-  m_ContentCreatorName(DCM_ContentCreatorName),
-  m_ContentCreatorIdentificationCode(),
-  m_IODRules()
+                                                       const OFString& contentCreatorName)
+    : m_InstanceNumber(DCM_InstanceNumber)
+    , m_ContentLabel(DCM_ContentLabel)
+    , m_ContentDescription(DCM_ContentDescription)
+    , m_AlternateContentDescription()
+    , m_ContentCreatorName(DCM_ContentCreatorName)
+    , m_ContentCreatorIdentificationCode()
+    , m_IODRules()
 {
-  resetRules();
-  setInstanceNumber(instanceNumber);
-  setContentLabel(contentLabel);
-  setContentDescription(contentDescription);
-  setContentCreatorName(contentCreatorName);
+    resetRules();
+    setInstanceNumber(instanceNumber);
+    setContentLabel(contentLabel);
+    setContentDescription(contentDescription);
+    setContentCreatorName(contentCreatorName);
 }
 
-
 void ContentIdentificationMacro::resetRules()
 {
-  m_IODRules.addRule(new IODRule(DCM_InstanceNumber,     "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_IODRules.addRule(new IODRule(DCM_ContentLabel,       "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_IODRules.addRule(new IODRule(DCM_ContentDescription, "1", "2", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_IODRules.addRule(new IODRule(DCM_ContentCreatorName, "1", "2", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_IODRules.addRule(new IODRule(DCM_AlternateContentDescriptionSequence, "1-n", "3", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_IODRules.addRule(new IODRule(DCM_ContentCreatorIdentificationCodeSequence, "1", "3", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_IODRules.addRule(new IODRule(DCM_InstanceNumber, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_IODRules.addRule(new IODRule(DCM_ContentLabel, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_IODRules.addRule(new IODRule(DCM_ContentDescription, "1", "2", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_IODRules.addRule(new IODRule(DCM_ContentCreatorName, "1", "2", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_IODRules.addRule(
+        new IODRule(DCM_AlternateContentDescriptionSequence, "1-n", "3", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_IODRules.addRule(
+        new IODRule(DCM_ContentCreatorIdentificationCodeSequence, "1", "3", getName(), DcmIODTypes::IE_INSTANCE),
+        OFTrue);
 }
 
-
 OFString ContentIdentificationMacro::getName() const
 {
-  return "ContentIdentificationMacro";
+    return "ContentIdentificationMacro";
 }
 
-
 IODRules& ContentIdentificationMacro::getIODRules()
 {
-  return m_IODRules;
+    return m_IODRules;
 }
 
-
-ContentIdentificationMacro::ContentIdentificationMacro(const ContentIdentificationMacro& rhs) :
-  m_InstanceNumber(DCM_InstanceNumber),
-  m_ContentLabel(DCM_ContentLabel),
-  m_ContentDescription(DCM_ContentDescription),
-  m_AlternateContentDescription(),
-  m_ContentCreatorName(DCM_ContentCreatorName),
-  m_ContentCreatorIdentificationCode(),
-  m_IODRules()
+ContentIdentificationMacro::ContentIdentificationMacro(const ContentIdentificationMacro& rhs)
+    : m_InstanceNumber(DCM_InstanceNumber)
+    , m_ContentLabel(DCM_ContentLabel)
+    , m_ContentDescription(DCM_ContentDescription)
+    , m_AlternateContentDescription()
+    , m_ContentCreatorName(DCM_ContentCreatorName)
+    , m_ContentCreatorIdentificationCode()
+    , m_IODRules()
 {
-  if (&rhs != this)
-  {
-    resetRules();
-    m_InstanceNumber = rhs.m_InstanceNumber;
-    m_ContentLabel = rhs.m_ContentLabel;
-    m_ContentDescription = rhs.m_ContentDescription;
-    m_ContentCreatorName = rhs.m_ContentCreatorName;
-    m_ContentCreatorIdentificationCode = rhs.m_ContentCreatorIdentificationCode;
-    /* perform deep vector copy */
-    OFVector<AlternateContentDescriptionItem*>::const_iterator it = rhs.m_AlternateContentDescription.begin();
-    while (it != rhs.m_AlternateContentDescription.end())
+    if (&rhs != this)
     {
-      m_AlternateContentDescription.push_back(new AlternateContentDescriptionItem(**it));
-      it++;
+        resetRules();
+        m_InstanceNumber                   = rhs.m_InstanceNumber;
+        m_ContentLabel                     = rhs.m_ContentLabel;
+        m_ContentDescription               = rhs.m_ContentDescription;
+        m_ContentCreatorName               = rhs.m_ContentCreatorName;
+        m_ContentCreatorIdentificationCode = rhs.m_ContentCreatorIdentificationCode;
+        /* perform deep vector copy */
+        OFVector<AlternateContentDescriptionItem*>::const_iterator it = rhs.m_AlternateContentDescription.begin();
+        while (it != rhs.m_AlternateContentDescription.end())
+        {
+            m_AlternateContentDescription.push_back(new AlternateContentDescriptionItem(**it));
+            it++;
+        }
     }
-  }
 }
 
-
 OFCondition ContentIdentificationMacro::create(const OFString& instanceNumber,
                                                const OFString& contentLabel,
                                                const OFString& contentDescription,
                                                const OFString& contentCreatorName,
                                                ContentIdentificationMacro*& result)
 {
-  result = new ContentIdentificationMacro();
-  if (!result)
-    return EC_MemoryExhausted;
-  OFCondition cond = result->setInstanceNumber(instanceNumber);
-  if (cond.good())
-  {
-    cond = result->setContentLabel(contentLabel);
-  }
-  if (cond.good())
-  {
-    cond = result->setContentDescription(contentDescription);
-  }
-  if (cond.good())
-  {
-    cond = result->setContentCreatorName(contentCreatorName);
-  }
-  if (cond.good())
-  {
-    cond = result->check();
-  }
-  if (cond.bad())
-  {
-    delete result;
-    result = NULL;
-  }
-  return cond;
+    result = new ContentIdentificationMacro();
+    if (!result)
+        return EC_MemoryExhausted;
+    OFCondition cond = result->setInstanceNumber(instanceNumber);
+    if (cond.good())
+    {
+        cond = result->setContentLabel(contentLabel);
+    }
+    if (cond.good())
+    {
+        cond = result->setContentDescription(contentDescription);
+    }
+    if (cond.good())
+    {
+        cond = result->setContentCreatorName(contentCreatorName);
+    }
+    if (cond.good())
+    {
+        cond = result->check();
+    }
+    if (cond.bad())
+    {
+        delete result;
+        result = NULL;
+    }
+    return cond;
 }
 
-
-
 ContentIdentificationMacro& ContentIdentificationMacro::operator=(const ContentIdentificationMacro& rhs)
 {
-  if (&rhs != this)
-  {
-    this->clearData();
-    m_InstanceNumber = rhs.m_InstanceNumber;
-    m_ContentLabel = rhs.m_ContentLabel;
-    m_ContentDescription = rhs.m_ContentDescription;
-    m_ContentCreatorName = rhs.m_ContentCreatorName;
-    m_ContentCreatorIdentificationCode = rhs.m_ContentCreatorIdentificationCode;
-    /* perform deep vector copy */
-    OFVector<AlternateContentDescriptionItem*>::const_iterator it = rhs.m_AlternateContentDescription.begin();
-    while (it != rhs.m_AlternateContentDescription.end())
+    if (&rhs != this)
     {
-      AlternateContentDescriptionItem* newItem = new AlternateContentDescriptionItem();
-      *newItem = **it;
-      m_AlternateContentDescription.push_back(newItem);
-      it++;
+        this->clearData();
+        m_InstanceNumber                   = rhs.m_InstanceNumber;
+        m_ContentLabel                     = rhs.m_ContentLabel;
+        m_ContentDescription               = rhs.m_ContentDescription;
+        m_ContentCreatorName               = rhs.m_ContentCreatorName;
+        m_ContentCreatorIdentificationCode = rhs.m_ContentCreatorIdentificationCode;
+        /* perform deep vector copy */
+        OFVector<AlternateContentDescriptionItem*>::const_iterator it = rhs.m_AlternateContentDescription.begin();
+        while (it != rhs.m_AlternateContentDescription.end())
+        {
+            AlternateContentDescriptionItem* newItem = new AlternateContentDescriptionItem();
+            *newItem                                 = **it;
+            m_AlternateContentDescription.push_back(newItem);
+            it++;
+        }
     }
-  }
-  return *this;
+    return *this;
 }
 
-
 ContentIdentificationMacro::~ContentIdentificationMacro()
 {
-  clearData();
+    clearData();
 }
 
-
 void ContentIdentificationMacro::clearData()
 {
-  m_InstanceNumber.clear();
-  m_ContentLabel.clear();
-  m_ContentDescription.clear();
-  DcmIODUtil::freeContainer(m_AlternateContentDescription);
-  m_ContentCreatorName.clear();
-  m_ContentCreatorIdentificationCode.clearData();
+    m_InstanceNumber.clear();
+    m_ContentLabel.clear();
+    m_ContentDescription.clear();
+    DcmIODUtil::freeContainer(m_AlternateContentDescription);
+    m_ContentCreatorName.clear();
+    m_ContentCreatorIdentificationCode.clearData();
 }
 
-
 OFCondition ContentIdentificationMacro::check(const OFBool quiet)
 {
-  (void)quiet;
-  OFCondition result;
-  OFBool failure = m_ContentLabel.isEmpty() || m_InstanceNumber.isEmpty();
-  if (!failure)
-  {
-    if (!m_AlternateContentDescription.empty())  // type 3
+    (void)quiet;
+    OFCondition result;
+    OFBool failure = m_ContentLabel.isEmpty() || m_InstanceNumber.isEmpty();
+    if (!failure)
     {
-      OFVector<AlternateContentDescriptionItem*>::iterator it = m_AlternateContentDescription.begin();
-      while ( it != m_AlternateContentDescription.end() && !failure)
-      {
-        OFString str;
-        (*it)->getContentDescription(str).good(); // type 1
-        failure = str.empty();
-        if (!failure)
+        if (!m_AlternateContentDescription.empty()) // type 3
         {
-          OFString meaning, value, designator;
-          (*it)->getLanguageCode().getCodeMeaning(meaning);
-          (*it)->getLanguageCode().getCodeValue(value);
-          (*it)->getLanguageCode().getCodeValue(designator);
-          failure = meaning.empty() || value.empty() || designator.empty();
+            OFVector<AlternateContentDescriptionItem*>::iterator it = m_AlternateContentDescription.begin();
+            while (it != m_AlternateContentDescription.end() && !failure)
+            {
+                OFString str;
+                (*it)->getContentDescription(str).good(); // type 1
+                failure = str.empty();
+                if (!failure)
+                {
+                    OFString meaning, value, designator;
+                    (*it)->getLanguageCode().getCodeMeaning(meaning);
+                    (*it)->getLanguageCode().getCodeValue(value);
+                    (*it)->getLanguageCode().getCodeValue(designator);
+                    failure = meaning.empty() || value.empty() || designator.empty();
+                }
+                it++;
+            }
         }
-        it++;
-      }
     }
-  }
-  if ( failure )
-    result = EC_IllegalParameter;
-  return result;
+    if (failure)
+        result = EC_IllegalParameter;
+    return result;
 }
 
-
-
-OFCondition ContentIdentificationMacro::getInstanceNumber(OFString& value,
-                                                          const signed long  pos) const
+OFCondition ContentIdentificationMacro::getInstanceNumber(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromElement(m_InstanceNumber, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_InstanceNumber, value, pos);
 }
 
-
-
-OFCondition ContentIdentificationMacro::getContentLabel(OFString& value,
-                                                        const signed long pos) const
+OFCondition ContentIdentificationMacro::getContentLabel(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromElement(m_ContentLabel, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_ContentLabel, value, pos);
 }
 
-
-OFCondition ContentIdentificationMacro::getContentDescription(OFString& value,
-                                                              const signed long pos) const
+OFCondition ContentIdentificationMacro::getContentDescription(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromElement(m_ContentDescription, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_ContentDescription, value, pos);
 }
 
-
-OFCondition ContentIdentificationMacro::getContentCreatorName(OFString& value,
-                                          const signed long pos) const
+OFCondition ContentIdentificationMacro::getContentCreatorName(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromElement(m_ContentCreatorName, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_ContentCreatorName, value, pos);
 }
 
-
 CodeSequenceMacro& ContentIdentificationMacro::getContentCreatorIdentificationCode()
 {
-  return m_ContentCreatorIdentificationCode;
+    return m_ContentCreatorIdentificationCode;
 }
 
-
-OFVector<ContentIdentificationMacro::AlternateContentDescriptionItem*>& ContentIdentificationMacro::getAlternateContentDescription()
+OFVector<ContentIdentificationMacro::AlternateContentDescriptionItem*>&
+ContentIdentificationMacro::getAlternateContentDescription()
 {
-  return m_AlternateContentDescription;
+    return m_AlternateContentDescription;
 }
 
-
-OFCondition ContentIdentificationMacro::setInstanceNumber(const OFString& value,
-                                                          const OFBool checkValue)
+OFCondition ContentIdentificationMacro::setInstanceNumber(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result;
-  if (checkValue)
-  {
-    result = (checkValue) ? DcmIntegerString::checkStringValue(value, "1") : EC_Normal;
-  }
-  if (result.good())
-  {
-    result = m_InstanceNumber.putOFStringArray(value);
-  }
-  return result;
+    OFCondition result;
+    if (checkValue)
+    {
+        result = (checkValue) ? DcmIntegerString::checkStringValue(value, "1") : EC_Normal;
+    }
+    if (result.good())
+    {
+        result = m_InstanceNumber.putOFStringArray(value);
+    }
+    return result;
 }
 
-
-OFCondition ContentIdentificationMacro::setContentLabel(const OFString& value,
-                                                        const OFBool checkValue)
+OFCondition ContentIdentificationMacro::setContentLabel(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, m_IODRules.getByTag(DCM_ContentLabel)->getVM()) : EC_Normal;
-  if (result.good())
-    result = m_ContentLabel.putOFStringArray(value);
-  return result;
+    OFCondition result = (checkValue)
+        ? DcmCodeString::checkStringValue(value, m_IODRules.getByTag(DCM_ContentLabel)->getVM())
+        : EC_Normal;
+    if (result.good())
+        result = m_ContentLabel.putOFStringArray(value);
+    return result;
 }
 
-
-OFCondition ContentIdentificationMacro::setContentDescription(const OFString& value,
-                                                              const OFBool checkValue)
+OFCondition ContentIdentificationMacro::setContentDescription(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, m_IODRules.getByTag(DCM_ContentDescription)->getVM()) : EC_Normal;
-  if (result.good())
-    result = m_ContentDescription.putOFStringArray(value);
-  return result;
+    OFCondition result = (checkValue)
+        ? DcmLongString::checkStringValue(value, m_IODRules.getByTag(DCM_ContentDescription)->getVM())
+        : EC_Normal;
+    if (result.good())
+        result = m_ContentDescription.putOFStringArray(value);
+    return result;
 }
 
-
-OFCondition ContentIdentificationMacro::setContentCreatorName(const OFString& value,
-                                                              const OFBool checkValue)
+OFCondition ContentIdentificationMacro::setContentCreatorName(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmPersonName::checkStringValue(value, m_IODRules.getByTag(DCM_ContentCreatorName)->getVM()) : EC_Normal;
-  if (result.good())
-    result = m_ContentCreatorName.putOFStringArray(value);
-  return result;
+    OFCondition result = (checkValue)
+        ? DcmPersonName::checkStringValue(value, m_IODRules.getByTag(DCM_ContentCreatorName)->getVM())
+        : EC_Normal;
+    if (result.good())
+        result = m_ContentCreatorName.putOFStringArray(value);
+    return result;
 }
 
-
-OFCondition ContentIdentificationMacro::read(DcmItem& source,
-                                             const OFBool clearOldData)
+OFCondition ContentIdentificationMacro::read(DcmItem& source, const OFBool clearOldData)
 {
-  OFCondition result;
+    OFCondition result;
 
-  if (clearOldData)
-    clearData();
+    if (clearOldData)
+        clearData();
 
-  /* flat elements */
+    /* flat elements */
 
-  DcmIODUtil::getAndCheckElementFromDataset(source, m_InstanceNumber, m_IODRules.getByTag(DCM_InstanceNumber));
-  DcmIODUtil::getAndCheckElementFromDataset(source, m_ContentLabel, m_IODRules.getByTag(DCM_ContentLabel));
-  DcmIODUtil::getAndCheckElementFromDataset(source, m_ContentDescription, m_IODRules.getByTag(DCM_ContentDescription));
-  DcmIODUtil::getAndCheckElementFromDataset(source, m_ContentCreatorName, m_IODRules.getByTag(DCM_ContentCreatorName));
+    DcmIODUtil::getAndCheckElementFromDataset(source, m_InstanceNumber, m_IODRules.getByTag(DCM_InstanceNumber));
+    DcmIODUtil::getAndCheckElementFromDataset(source, m_ContentLabel, m_IODRules.getByTag(DCM_ContentLabel));
+    DcmIODUtil::getAndCheckElementFromDataset(
+        source, m_ContentDescription, m_IODRules.getByTag(DCM_ContentDescription));
+    DcmIODUtil::getAndCheckElementFromDataset(
+        source, m_ContentCreatorName, m_IODRules.getByTag(DCM_ContentCreatorName));
 
-  /* sub sequences */
-  IODRule *rule = m_IODRules.getByTag(DCM_AlternateContentDescriptionSequence);
-  DcmIODUtil::readSubSequence<OFVector<AlternateContentDescriptionItem*> >
-  ( source,
-    DCM_AlternateContentDescriptionSequence,
-    m_AlternateContentDescription,
-    rule->getVM(),
-    rule->getType(),
-    "ContentIdentificationMacro" );
+    /* sub sequences */
+    IODRule* rule = m_IODRules.getByTag(DCM_AlternateContentDescriptionSequence);
+    DcmIODUtil::readSubSequence<OFVector<AlternateContentDescriptionItem*> >(source,
+                                                                             DCM_AlternateContentDescriptionSequence,
+                                                                             m_AlternateContentDescription,
+                                                                             rule->getVM(),
+                                                                             rule->getType(),
+                                                                             "ContentIdentificationMacro");
 
-  rule = m_IODRules.getByTag(DCM_ContentCreatorIdentificationCodeSequence);
-  DcmIODUtil::readSingleItem<CodeSequenceMacro>
-  (
-    source,
-   DCM_ContentCreatorIdentificationCodeSequence,
-   m_ContentCreatorIdentificationCode,
-   rule->getType(),
-   "ContentIdentificationMacro");
+    rule = m_IODRules.getByTag(DCM_ContentCreatorIdentificationCodeSequence);
+    DcmIODUtil::readSingleItem<CodeSequenceMacro>(source,
+                                                  DCM_ContentCreatorIdentificationCodeSequence,
+                                                  m_ContentCreatorIdentificationCode,
+                                                  rule->getType(),
+                                                  "ContentIdentificationMacro");
 
-  return result;
+    return result;
 }
 
-
 OFCondition ContentIdentificationMacro::write(DcmItem& item)
 {
-  OFCondition result = EC_Normal;
-
-  /* flat elements */
-  DcmIODUtil::copyElementToDataset(result, item, m_InstanceNumber,  m_IODRules.getByTag(DCM_InstanceNumber));
-  DcmIODUtil::copyElementToDataset(result, item, m_ContentLabel, m_IODRules.getByTag(DCM_ContentLabel));
-  DcmIODUtil::copyElementToDataset(result, item, m_ContentDescription, m_IODRules.getByTag(DCM_ContentDescription));
-  DcmIODUtil::copyElementToDataset(result, item, m_ContentCreatorName,  m_IODRules.getByTag(DCM_ContentCreatorName));
-
-  IODRule *rule = m_IODRules.getByTag(DCM_ContentCreatorIdentificationCodeSequence);
-  DcmIODUtil::writeSingleItem<CodeSequenceMacro>
-  (
-    result,
-    DCM_ContentCreatorIdentificationCodeSequence,
-    m_ContentCreatorIdentificationCode,
-    item,
-    rule->getType(),
-    "ContentIdentificationMacro"
-  );
-
-  rule = m_IODRules.getByTag(DCM_AlternateContentDescriptionSequence);
-  DcmIODUtil::writeSubSequence< OFVector<ContentIdentificationMacro::AlternateContentDescriptionItem*> >
-  (
-    result,
-    DCM_AlternateContentDescriptionSequence,
-    m_AlternateContentDescription,
-    item,
-    rule->getVM(),
-    rule->getType(),
-    "ContentIdentificationMacro"
-  );
-
-  return result;
+    OFCondition result = EC_Normal;
+
+    /* flat elements */
+    DcmIODUtil::copyElementToDataset(result, item, m_InstanceNumber, m_IODRules.getByTag(DCM_InstanceNumber));
+    DcmIODUtil::copyElementToDataset(result, item, m_ContentLabel, m_IODRules.getByTag(DCM_ContentLabel));
+    DcmIODUtil::copyElementToDataset(result, item, m_ContentDescription, m_IODRules.getByTag(DCM_ContentDescription));
+    DcmIODUtil::copyElementToDataset(result, item, m_ContentCreatorName, m_IODRules.getByTag(DCM_ContentCreatorName));
+
+    IODRule* rule = m_IODRules.getByTag(DCM_ContentCreatorIdentificationCodeSequence);
+    DcmIODUtil::writeSingleItem<CodeSequenceMacro>(result,
+                                                   DCM_ContentCreatorIdentificationCodeSequence,
+                                                   m_ContentCreatorIdentificationCode,
+                                                   item,
+                                                   rule->getType(),
+                                                   "ContentIdentificationMacro");
+
+    rule = m_IODRules.getByTag(DCM_AlternateContentDescriptionSequence);
+    DcmIODUtil::writeSubSequence<OFVector<ContentIdentificationMacro::AlternateContentDescriptionItem*> >(
+        result,
+        DCM_AlternateContentDescriptionSequence,
+        m_AlternateContentDescription,
+        item,
+        rule->getVM(),
+        rule->getType(),
+        "ContentIdentificationMacro");
 
+    return result;
 }
 
-
 // ---------------- ContentIdentificationMacro::AlternateContentDescriptionItem -----------------
 
 ContentIdentificationMacro::AlternateContentDescriptionItem::AlternateContentDescriptionItem()
-  : m_ContentDescription(DCM_ContentDescription),
-    m_LanguageCode()
+    : m_ContentDescription(DCM_ContentDescription)
+    m_LanguageCode()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
 ContentIdentificationMacro::AlternateContentDescriptionItem::~AlternateContentDescriptionItem()
 {
-  m_LanguageCode.clearData();
+    m_LanguageCode.clearData();
 }
 
-
 void ContentIdentificationMacro::AlternateContentDescriptionItem::clearData()
 {
-  m_ContentDescription.clear();
-  m_LanguageCode.clearData();
+    m_ContentDescription.clear();
+    m_LanguageCode.clearData();
 }
 
-
 OFCondition ContentIdentificationMacro::AlternateContentDescriptionItem::read(DcmItem& source,
                                                                               const OFBool clearOldData)
 {
-  OFCondition result;
-  if (clearOldData)
-    clearData();
+    OFCondition result;
+    if (clearOldData)
+        clearData();
 
-  DcmIODUtil::getAndCheckElementFromDataset(source, m_ContentDescription, "1", "1", "ContentIdentificationMacro");
-  DcmIODUtil::readSingleItem<CodeSequenceMacro>
-  (
-    source,
-    DCM_LanguageCodeSequence,
-    m_LanguageCode,
-    "1",
-    "ContentIdentificationMacro"
-  );
+    DcmIODUtil::getAndCheckElementFromDataset(source, m_ContentDescription, "1", "1", "ContentIdentificationMacro");
+    DcmIODUtil::readSingleItem<CodeSequenceMacro>(
+        source, DCM_LanguageCodeSequence, m_LanguageCode, "1", "ContentIdentificationMacro");
 
-  return result;
+    return result;
 }
 
-
-OFCondition ContentIdentificationMacro::AlternateContentDescriptionItem::getContentDescription(OFString& value,
-                                                                                               const long signed int pos)
+OFCondition
+ContentIdentificationMacro::AlternateContentDescriptionItem::getContentDescription(OFString& value,
+                                                                                   const long signed int pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_ContentDescription, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_ContentDescription, value, pos);
 }
 
-
-
 CodeSequenceMacro& ContentIdentificationMacro::AlternateContentDescriptionItem::getLanguageCode()
 {
-  return m_LanguageCode;
+    return m_LanguageCode;
 }
 
-
-
 OFCondition ContentIdentificationMacro::AlternateContentDescriptionItem::write(DcmItem& item)
 {
-  OFCondition result = EC_Normal;
-  // write to item
-  DcmIODUtil::copyElementToDataset(result, item, m_ContentDescription, "1", "1", "ContentIdentificationMacro");
-  DcmIODUtil::writeSingleItem<CodeSequenceMacro>
-  (  result,
-     DCM_LanguageCodeSequence,
-     m_LanguageCode,
-     item,
-     "1",
-     "ContentIdentificationMacro"
-  );
-  return result;
+    OFCondition result = EC_Normal;
+    // write to item
+    DcmIODUtil::copyElementToDataset(result, item, m_ContentDescription, "1", "1", "ContentIdentificationMacro");
+    DcmIODUtil::writeSingleItem<CodeSequenceMacro>(
+        result, DCM_LanguageCodeSequence, m_LanguageCode, item, "1", "ContentIdentificationMacro");
+    return result;
 }
 
-
 OFCondition ContentIdentificationMacro::AlternateContentDescriptionItem::setContentDescription(const OFString& value,
                                                                                                const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_ContentDescription.putOFStringArray(value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_ContentDescription.putOFStringArray(value);
+    return result;
 }
 
-
 // -------------------- HL7HierarchicDesignatorMacro --------------------
 
-
 HL7HierarchicDesignatorMacro::HL7HierarchicDesignatorMacro(IODComponent* parent)
-: IODComponent(parent)
+    : IODComponent(parent)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-HL7HierarchicDesignatorMacro::HL7HierarchicDesignatorMacro(OFshared_ptr< DcmItem > item,
-                                                           OFshared_ptr< IODRules > rules,
+HL7HierarchicDesignatorMacro::HL7HierarchicDesignatorMacro(OFshared_ptr<DcmItem> item,
+                                                           OFshared_ptr<IODRules> rules,
                                                            IODComponent* parent)
-: IODComponent(item, rules, parent)
+    : IODComponent(item, rules, parent)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 OFCondition HL7HierarchicDesignatorMacro::getUniversalEntityID(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_UniversalEntityID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_UniversalEntityID, *m_Item, value, pos);
 }
 
-
 OFCondition HL7HierarchicDesignatorMacro::getLocalNamespaceEntityID(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_LocalNamespaceEntityID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_LocalNamespaceEntityID, *m_Item, value, pos);
 }
 
-
 OFCondition HL7HierarchicDesignatorMacro::getUniversalEntityIDType(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_UniversalEntityIDType, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_UniversalEntityIDType, *m_Item, value, pos);
 }
 
-
 OFString HL7HierarchicDesignatorMacro::getName() const
 {
-  return "HL7HierarchicDesignatorMacro";
+    return "HL7HierarchicDesignatorMacro";
 }
 
-
 void HL7HierarchicDesignatorMacro::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_UniversalEntityID, "1","1C", "getName()", DcmIODTypes::IE_UNDEFINED), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_LocalNamespaceEntityID, "1","1C", "getName()", DcmIODTypes::IE_UNDEFINED), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_UniversalEntityIDType, "1","1C", "getName()", DcmIODTypes::IE_UNDEFINED), OFTrue);
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_UniversalEntityID, "1", "1C", "getName()", DcmIODTypes::IE_UNDEFINED), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_LocalNamespaceEntityID, "1", "1C", "getName()", DcmIODTypes::IE_UNDEFINED),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_UniversalEntityIDType, "1", "1C", "getName()", DcmIODTypes::IE_UNDEFINED), OFTrue);
 }
 
-
-OFCondition HL7HierarchicDesignatorMacro::setLocalNamespaceEntityID(const OFString& value,
-                                                                    const OFBool checkValue)
+OFCondition HL7HierarchicDesignatorMacro::setLocalNamespaceEntityID(const OFString& value, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertOFStringArray(DCM_LocalNamespaceEntityID,value);
+    (void)checkValue;
+    return m_Item->putAndInsertOFStringArray(DCM_LocalNamespaceEntityID, value);
 }
 
-
-OFCondition HL7HierarchicDesignatorMacro::setUniversalEntityID(const OFString& value,
-                                                               const OFBool checkValue)
+OFCondition HL7HierarchicDesignatorMacro::setUniversalEntityID(const OFString& value, const OFBool checkValue)
 {
-  (void) checkValue;
-  return m_Item->putAndInsertOFStringArray(DCM_UniversalEntityID,value);
+    (void)checkValue;
+    return m_Item->putAndInsertOFStringArray(DCM_UniversalEntityID, value);
 }
 
-
-OFCondition HL7HierarchicDesignatorMacro::setUniversalEntityIDType(const OFString& value,
-                                                                   const OFBool checkValue)
+OFCondition HL7HierarchicDesignatorMacro::setUniversalEntityIDType(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_UniversalEntityID,value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_UniversalEntityID, value);
+    return result;
 }
 
-
 // -------------------- Mandatory View and Slice Progression Direction Macro --------------------
 
-
-MandatoryViewAndSliceProgressionDirectionMacro::MandatoryViewAndSliceProgressionDirectionMacro(OFshared_ptr< DcmItem > item,
-                                                                                               OFshared_ptr< IODRules > rules,
-                                                                                               IODComponent* parent)
-: IODComponent(item, rules, parent),
-  m_ViewCodeSequence(),
-  m_ViewModifierCode()
+MandatoryViewAndSliceProgressionDirectionMacro::MandatoryViewAndSliceProgressionDirectionMacro(
+    OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules, IODComponent* parent)
+    : IODComponent(item, rules, parent)
+    , m_ViewCodeSequence()
+    , m_ViewModifierCode()
 {
-  resetRules();
+    resetRules();
 }
 
-
-
 MandatoryViewAndSliceProgressionDirectionMacro::MandatoryViewAndSliceProgressionDirectionMacro(IODComponent* parent)
-: IODComponent(parent),
-  m_ViewCodeSequence(),
-  m_ViewModifierCode()
+    : IODComponent(parent)
+    , m_ViewCodeSequence()
+    , m_ViewModifierCode()
 {
-  resetRules();
+    resetRules();
 }
 
-
 OFString MandatoryViewAndSliceProgressionDirectionMacro::getName() const
 {
-  return "MandatoryViewAndSliceProgressionDirectionMacro";
+    return "MandatoryViewAndSliceProgressionDirectionMacro";
 }
 
-
 void MandatoryViewAndSliceProgressionDirectionMacro::resetRules()
 {
-  m_Rules->addRule(new IODRule(DCM_ViewCodeSequence, "1","1", getName(), DcmIODTypes::IE_UNDEFINED), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ViewModifierCodeSequence, "1-n","2C", getName(), DcmIODTypes::IE_UNDEFINED), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_SliceProgressionDirection, "1","1C", getName(), DcmIODTypes::IE_UNDEFINED), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ViewCodeSequence, "1", "1", getName(), DcmIODTypes::IE_UNDEFINED), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ViewModifierCodeSequence, "1-n", "2C", getName(), DcmIODTypes::IE_UNDEFINED),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_SliceProgressionDirection, "1", "1C", getName(), DcmIODTypes::IE_UNDEFINED),
+                     OFTrue);
 }
 
-
 void MandatoryViewAndSliceProgressionDirectionMacro::clearData()
 {
-  DcmIODUtil::freeContainer(m_ViewModifierCode);
-  m_ViewCodeSequence.clearData();
-  IODComponent::clearData();
+    DcmIODUtil::freeContainer(m_ViewModifierCode);
+    m_ViewCodeSequence.clearData();
+    IODComponent::clearData();
 }
 
-
-OFCondition MandatoryViewAndSliceProgressionDirectionMacro::read(DcmItem& source,
-                                                                 const OFBool clearOldData)
+OFCondition MandatoryViewAndSliceProgressionDirectionMacro::read(DcmItem& source, const OFBool clearOldData)
 {
-  if (clearOldData)
-  {
-    m_ViewCodeSequence.clearData();
-    DcmIODUtil::freeContainer(m_ViewModifierCode);
-  }
-  OFCondition result = EC_Normal;
-  DcmIODUtil::readSingleItem(source, DCM_ViewCodeSequence, m_ViewCodeSequence, m_Rules->getByTag(DCM_ViewCodeSequence));
-  DcmIODUtil::readSubSequence(source, DCM_ViewCodeSequence, m_ViewModifierCode, m_Rules->getByTag(DCM_ViewCodeSequence));
-  IODComponent::read(source, clearOldData);
-  return EC_Normal;
+    if (clearOldData)
+    {
+        m_ViewCodeSequence.clearData();
+        DcmIODUtil::freeContainer(m_ViewModifierCode);
+    }
+    OFCondition result = EC_Normal;
+    DcmIODUtil::readSingleItem(
+        source, DCM_ViewCodeSequence, m_ViewCodeSequence, m_Rules->getByTag(DCM_ViewCodeSequence));
+    DcmIODUtil::readSubSequence(
+        source, DCM_ViewCodeSequence, m_ViewModifierCode, m_Rules->getByTag(DCM_ViewCodeSequence));
+    IODComponent::read(source, clearOldData);
+    return EC_Normal;
 }
 
-
 OFCondition MandatoryViewAndSliceProgressionDirectionMacro::write(DcmItem& item)
 {
-  OFCondition result = EC_Normal;
-  DcmIODUtil::writeSingleItem(result, DCM_ViewCodeSequence, m_ViewCodeSequence, *m_Item, m_Rules->getByTag(DCM_ViewCodeSequence));
-  DcmIODUtil::writeSubSequence(result, DCM_ViewCodeSequence, m_ViewModifierCode, *m_Item, m_Rules->getByTag(DCM_ViewModifierCodeSequence));
-  if (result.good()) result = IODComponent::write(item);
-  return result;
+    OFCondition result = EC_Normal;
+    DcmIODUtil::writeSingleItem(
+        result, DCM_ViewCodeSequence, m_ViewCodeSequence, *m_Item, m_Rules->getByTag(DCM_ViewCodeSequence));
+    DcmIODUtil::writeSubSequence(
+        result, DCM_ViewCodeSequence, m_ViewModifierCode, *m_Item, m_Rules->getByTag(DCM_ViewModifierCodeSequence));
+    if (result.good())
+        result = IODComponent::write(item);
+    return result;
 }
 
-
 CodeSequenceMacro& MandatoryViewAndSliceProgressionDirectionMacro::getViewCode()
 {
-  return m_ViewCodeSequence;
+    return m_ViewCodeSequence;
 }
 
-
-OFVector< CodeSequenceMacro* >& MandatoryViewAndSliceProgressionDirectionMacro::getViewModifierCode()
+OFVector<CodeSequenceMacro*>& MandatoryViewAndSliceProgressionDirectionMacro::getViewModifierCode()
 {
-  return m_ViewModifierCode;
+    return m_ViewModifierCode;
 }
index bf57c13fbbc8e4375c40bc266704341484b9a0c9..0eb1b540b93d3c767b14ba889d81543b90d847fb 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016-2018, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmiod/iodtypes.h"
 #include "dcmtk/dcmiod/iodreferences.h"
-#include "dcmtk/dcmiod/iodutil.h"
-#include "dcmtk/dcmdata/dcerror.h"
+#include "dcmtk/config/osconfig.h"
 #include "dcmtk/dcmdata/dcdatset.h"
-#include "dcmtk/dcmdata/dcvrui.h"
-#include "dcmtk/dcmdata/dcvrlo.h"
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmdata/dcerror.h"
 #include "dcmtk/dcmdata/dcfilefo.h"
-
+#include "dcmtk/dcmdata/dcvrlo.h"
+#include "dcmtk/dcmdata/dcvrui.h"
+#include "dcmtk/dcmiod/iodtypes.h"
+#include "dcmtk/dcmiod/iodutil.h"
 
 // ------------------- class IODReference -------------------------------
 
 IODReference::IODReference(const IODReference::MAX_LEVEL level)
-: m_PatientID(),
-  m_StudyInstanceUID(),
-  m_SeriesInstanceUID(),
-  m_SOPClassUID(),
-  m_SOPInstanceUID(),
-  m_Level(level)
+    : m_PatientID()
+    , m_StudyInstanceUID()
+    , m_SeriesInstanceUID()
+    , m_SOPClassUID()
+    , m_SOPInstanceUID()
+    , m_Level(level)
 {
 }
 
-
 IODReference::IODReference()
-: m_PatientID(),
-  m_StudyInstanceUID(),
-  m_SeriesInstanceUID(),
-  m_SOPClassUID(),
-  m_SOPInstanceUID(),
-  m_Level(LEVEL_STUDY)
+    : m_PatientID()
+    , m_StudyInstanceUID()
+    , m_SeriesInstanceUID()
+    , m_SOPClassUID()
+    , m_SOPInstanceUID()
+    , m_Level(LEVEL_STUDY)
 {
 }
 
 IODReference::~IODReference()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
-
 void IODReference::clear()
 {
-  m_StudyInstanceUID.clear();
-  m_SeriesInstanceUID.clear();
-  m_SOPClassUID.clear();
-  m_SOPInstanceUID.clear();
+    m_StudyInstanceUID.clear();
+    m_SeriesInstanceUID.clear();
+    m_SOPClassUID.clear();
+    m_SOPInstanceUID.clear();
 }
 
-
 OFBool IODReferences::add(IODReference* ref)
 {
-  if (ref->check().good())
-  {
-    m_References.push_back(ref);
-    return OFTrue;
-  }
-  return OFFalse;
+    if (ref->check().good())
+    {
+        m_References.push_back(ref);
+        return OFTrue;
+    }
+    return OFFalse;
 }
 
-
 OFBool IODReference::readFromItem(DcmItem& item)
 {
-  if (m_Level >= LEVEL_PATIENT)
-  {
-    item.findAndGetOFString(DCM_PatientID, m_PatientID);
-  }
-  if (m_Level >= LEVEL_STUDY)
-  {
-    item.findAndGetOFString(DCM_StudyInstanceUID, m_StudyInstanceUID);
-  }
-  if (m_Level >= LEVEL_SERIES)
-  {
-    item.findAndGetOFString(DCM_SeriesInstanceUID, m_SeriesInstanceUID);
-  }
-  if (m_Level >= LEVEL_INSTANCE)
-  {
-    item.findAndGetOFString(DCM_SOPClassUID, m_SOPClassUID);
-    item.findAndGetOFString(DCM_SOPInstanceUID, m_SOPInstanceUID);
-  }
-  return check().good();
+    if (m_Level >= LEVEL_PATIENT)
+    {
+        item.findAndGetOFString(DCM_PatientID, m_PatientID);
+    }
+    if (m_Level >= LEVEL_STUDY)
+    {
+        item.findAndGetOFString(DCM_StudyInstanceUID, m_StudyInstanceUID);
+    }
+    if (m_Level >= LEVEL_SERIES)
+    {
+        item.findAndGetOFString(DCM_SeriesInstanceUID, m_SeriesInstanceUID);
+    }
+    if (m_Level >= LEVEL_INSTANCE)
+    {
+        item.findAndGetOFString(DCM_SOPClassUID, m_SOPClassUID);
+        item.findAndGetOFString(DCM_SOPInstanceUID, m_SOPInstanceUID);
+    }
+    return check().good();
 }
 
-
 OFBool IODReference::readFromFile(const OFString& filename)
 {
-  clear();
-  DcmFileFormat ff;
-  OFCondition result = ff.loadFile(filename.c_str());
-  if (result.good())
-  {
-    DcmDataset* dset = ff.getDataset();
-    return readFromItem(*dset);
-  }
-  return OFFalse;
+    clear();
+    DcmFileFormat ff;
+    OFCondition result = ff.loadFile(filename.c_str());
+    if (result.good())
+    {
+        DcmDataset* dset = ff.getDataset();
+        return readFromItem(*dset);
+    }
+    return OFFalse;
 }
 
-
 OFCondition IODReferences::readTractographyReferencedInstanceSequence(DcmItem& source)
 {
-  size_t omitted = 0;
-  size_t added = 0;
-  DcmSequenceOfItems *seq = NULL;
-  OFCondition result = source.findAndGetSequence(DCM_ReferencedInstanceSequence, seq);
-  if (result.good())
-  {
-    DcmItem* item = NULL;
-    item = OFstatic_cast(DcmItem*, seq->nextInContainer(item));
-    while ( (item != NULL) && result.good() )
+    size_t omitted          = 0;
+    size_t added            = 0;
+    DcmSequenceOfItems* seq = NULL;
+    OFCondition result      = source.findAndGetSequence(DCM_ReferencedInstanceSequence, seq);
+    if (result.good())
     {
-      IODImageReference* ref = new IODImageReference(IODReference::LEVEL_INSTANCE);
-      if (!ref)
-      {
-        return EC_MemoryExhausted;
-      }
-      item->findAndGetOFString(DCM_ReferencedSOPClassUID, ref->m_SOPClassUID);
-      item->findAndGetOFString(DCM_ReferencedSOPInstanceUID, ref->m_SOPInstanceUID);
-      // if present, copy referenced frame numbers
-      DcmElement* elem = NULL;
-      if (item->findAndGetElement(DCM_ReferencedFrameNumber, elem).good())
-      {
-        unsigned long vm = elem->getNumberOfValues();
-        for (unsigned long f = 0; f < vm; f++)
+        DcmItem* item = NULL;
+        item          = OFstatic_cast(DcmItem*, seq->nextInContainer(item));
+        while ((item != NULL) && result.good())
         {
-          Sint32 val = 0;
-          if (elem->getSint32(val, f).good())
-          {
-            if (val >= 0)
-              ref->m_ReferencedFrameNumber.push_back( OFstatic_cast(Uint32, val) );
+            IODImageReference* ref = new IODImageReference(IODReference::LEVEL_INSTANCE);
+            if (!ref)
+            {
+                return EC_MemoryExhausted;
+            }
+            item->findAndGetOFString(DCM_ReferencedSOPClassUID, ref->m_SOPClassUID);
+            item->findAndGetOFString(DCM_ReferencedSOPInstanceUID, ref->m_SOPInstanceUID);
+            // if present, copy referenced frame numbers
+            DcmElement* elem = NULL;
+            if (item->findAndGetElement(DCM_ReferencedFrameNumber, elem).good())
+            {
+                unsigned long vm = elem->getNumberOfValues();
+                for (unsigned long f = 0; f < vm; f++)
+                {
+                    Sint32 val = 0;
+                    if (elem->getSint32(val, f).good())
+                    {
+                        if (val >= 0)
+                            ref->m_ReferencedFrameNumber.push_back(OFstatic_cast(Uint32, val));
+                        else
+                        {
+                            DCMIOD_WARN("Referenced Frame Number must be > 0 but is " << val
+                                                                                      << ", omitting frame reference");
+                        }
+                    }
+                    else
+                    {
+                        DCMIOD_WARN("Cannot get Referenced Frame Number from position #"
+                                    << f << " omitting frame reference");
+                    }
+                }
+            }
+            result = ref->check();
+            if (result.good())
+            {
+                added++;
+                m_References.push_back(ref);
+            }
             else
             {
-              DCMIOD_WARN("Referenced Frame Number must be > 0 but is " << val << ", omitting frame reference");
+                DCMIOD_WARN("Could not read Image reference (invalid?): " << (*ref).toString());
+                omitted++;
+                delete ref;
+                ref = NULL;
             }
-          }
-          else
-          {
-            DCMIOD_WARN("Cannot get Referenced Frame Number from position #" << f << " omitting frame reference");
-          }
+            item = OFstatic_cast(DcmItem*, seq->nextInContainer(item));
         }
-      }
-      result = ref->check();
-      if (result.good())
-      {
-        added++;
-        m_References.push_back(ref);
-      }
-      else
-      {
-        DCMIOD_WARN("Could not read Image reference (invalid?): " << (*ref).toString());
-        omitted++;
-        delete ref;
-        ref = NULL;
-      }
-      item = OFstatic_cast(DcmItem*, seq->nextInContainer(item));
     }
-  }
-  if ( (omitted > 0) && (added > 0) )
-  {
-    return IOD_EC_ReferencesOmitted;
-  }
-  else if (omitted > 0)
-  {
-    return IOD_EC_InvalidReference;
-  }
-  return EC_Normal;
-}
-
-
-
-OFCondition IODReferences::writeTractographyReferencedInstanceSequence(DcmItem& item)
-{
-  OFVector<IODReference*>::iterator it = m_References.begin();
-  item.findAndDeleteElement(DCM_ReferencedInstanceSequence);
-  DcmItem *seqItem = NULL;
-  size_t numItem = 0;
-  OFCondition result;
-  while ( (it != m_References.end() && result.good()) )
-  {
-    if (result.good())
+    if ((omitted > 0) && (added > 0))
     {
-      result = item.findOrCreateSequenceItem(DCM_ReferencedInstanceSequence, seqItem, OFstatic_cast(long, numItem));
-      numItem++;
+        return IOD_EC_ReferencesOmitted;
     }
-    if (result.good())
+    else if (omitted > 0)
     {
-      result = seqItem->putAndInsertOFStringArray(DCM_ReferencedSOPClassUID, (*it)->m_SOPClassUID);
+        return IOD_EC_InvalidReference;
     }
-    if (result.good()) result = seqItem->putAndInsertOFStringArray(DCM_ReferencedSOPInstanceUID, (*it)->m_SOPInstanceUID);
-    if (result.good())
+    return EC_Normal;
+}
+
+OFCondition IODReferences::writeTractographyReferencedInstanceSequence(DcmItem& item)
+{
+    OFVector<IODReference*>::iterator it = m_References.begin();
+    item.findAndDeleteElement(DCM_ReferencedInstanceSequence);
+    DcmItem* seqItem = NULL;
+    size_t numItem   = 0;
+    OFCondition result;
+    while ((it != m_References.end() && result.good()))
     {
-      if ( (*it)->getType() == IODReference::IMAGE )
-      {
         if (result.good())
         {
-          IODImageReference* ref = OFstatic_cast(IODImageReference*, *it);
-          if (ref && !ref->m_ReferencedFrameNumber.empty())
-          {
-            OFStringStream oss;
-            for (size_t f = 0; f < ref->m_ReferencedFrameNumber.size(); f++)
+            result
+                = item.findOrCreateSequenceItem(DCM_ReferencedInstanceSequence, seqItem, OFstatic_cast(long, numItem));
+            numItem++;
+        }
+        if (result.good())
+        {
+            result = seqItem->putAndInsertOFStringArray(DCM_ReferencedSOPClassUID, (*it)->m_SOPClassUID);
+        }
+        if (result.good())
+            result = seqItem->putAndInsertOFStringArray(DCM_ReferencedSOPInstanceUID, (*it)->m_SOPInstanceUID);
+        if (result.good())
+        {
+            if ((*it)->getType() == IODReference::IMAGE)
             {
-              oss << ref->m_ReferencedFrameNumber[f] << "\\";
+                if (result.good())
+                {
+                    IODImageReference* ref = OFstatic_cast(IODImageReference*, *it);
+                    if (ref && !ref->m_ReferencedFrameNumber.empty())
+                    {
+                        OFStringStream oss;
+                        for (size_t f = 0; f < ref->m_ReferencedFrameNumber.size(); f++)
+                        {
+                            oss << ref->m_ReferencedFrameNumber[f] << "\\";
+                        }
+                        OFSTRINGSTREAM_GETOFSTRING(oss, frameRefs)
+                        // Insert all references into Referenced Frame Number attribute.
+                        // Remove superfluous "\" at the end of the string.
+                        result = seqItem->putAndInsertOFStringArray(DCM_ReferencedFrameNumber,
+                                                                    frameRefs.substr(0, frameRefs.size() - 1));
+                    }
+                }
             }
-            OFSTRINGSTREAM_GETOFSTRING(oss, frameRefs)
-            // Insert all references into Referenced Frame Number attribute.
-            // Remove superfluous "\" at the end of the string.
-            result = seqItem->putAndInsertOFStringArray(DCM_ReferencedFrameNumber, frameRefs.substr(0, frameRefs.size() - 1));
-          }
         }
-      }
+        it++;
     }
-    it++;
-  }
-  if (result.bad())
-  {
-    item.findAndDeleteElement(DCM_ReferencedInstanceSequence);
-  }
-  return result;
+    if (result.bad())
+    {
+        item.findAndDeleteElement(DCM_ReferencedInstanceSequence);
+    }
+    return result;
 }
 
-
 OFString IODReference::toString() const
 {
-  char buf[400];
-  sprintf(buf, "Study/Series/SOPClass/SOPInstance UIDs: %s/%s/%s/%s", m_StudyInstanceUID.c_str(), m_SeriesInstanceUID.c_str(), m_SOPClassUID.c_str(), m_SOPInstanceUID.c_str());
-  return buf;
+    char buf[400];
+    sprintf(buf,
+            "Study/Series/SOPClass/SOPInstance UIDs: %s/%s/%s/%s",
+            m_StudyInstanceUID.c_str(),
+            m_SeriesInstanceUID.c_str(),
+            m_SOPClassUID.c_str(),
+            m_SOPInstanceUID.c_str());
+    return buf;
 }
 
-
 OFCondition IODReference::check() const
 {
-  OFCondition result;
-  if (m_Level >= LEVEL_PATIENT)
-  {
-    if (!m_PatientID.empty())
-    {
-      result = DcmLongString::checkStringValue(m_PatientID);
-    }
-    else
-    {
-      result = IOD_EC_InvalidElementValue;
-    }
-  }
-  if (result.good() && (m_Level >= LEVEL_STUDY))
-  {
-    if (!m_StudyInstanceUID.empty())
-    {
-      result= DcmUniqueIdentifier::checkStringValue(m_StudyInstanceUID, "1");
-    }
-    else
-    {
-      result = IOD_EC_InvalidElementValue;
-    }
-  }
-  if (result.good() && (m_Level >= LEVEL_SERIES))
-  {
-    if (!m_SeriesInstanceUID.empty())
-    {
-      result = DcmUniqueIdentifier::checkStringValue(m_SeriesInstanceUID, "1");
-    }
-    else
+    OFCondition result;
+    if (m_Level >= LEVEL_PATIENT)
     {
-      result = IOD_EC_InvalidElementValue;
+        if (!m_PatientID.empty())
+        {
+            result = DcmLongString::checkStringValue(m_PatientID);
+        }
+        else
+        {
+            result = IOD_EC_InvalidElementValue;
+        }
     }
-  }
-  if (result.good() && (m_Level >= LEVEL_INSTANCE))
-  {
-    if (!m_SOPClassUID.empty())
+    if (result.good() && (m_Level >= LEVEL_STUDY))
     {
-      result = DcmUniqueIdentifier::checkStringValue(m_SOPClassUID, "1");
+        if (!m_StudyInstanceUID.empty())
+        {
+            result = DcmUniqueIdentifier::checkStringValue(m_StudyInstanceUID, "1");
+        }
+        else
+        {
+            result = IOD_EC_InvalidElementValue;
+        }
     }
-    else
+    if (result.good() && (m_Level >= LEVEL_SERIES))
     {
-      result = IOD_EC_InvalidElementValue;
+        if (!m_SeriesInstanceUID.empty())
+        {
+            result = DcmUniqueIdentifier::checkStringValue(m_SeriesInstanceUID, "1");
+        }
+        else
+        {
+            result = IOD_EC_InvalidElementValue;
+        }
     }
-  }
-  if (result.good() && (m_Level >= LEVEL_INSTANCE))
-  {
-    if (!m_SOPInstanceUID.empty())
+    if (result.good() && (m_Level >= LEVEL_INSTANCE))
     {
-      result = DcmUniqueIdentifier::checkStringValue(m_SOPInstanceUID, "1");
+        if (!m_SOPClassUID.empty())
+        {
+            result = DcmUniqueIdentifier::checkStringValue(m_SOPClassUID, "1");
+        }
+        else
+        {
+            result = IOD_EC_InvalidElementValue;
+        }
     }
-    else
+    if (result.good() && (m_Level >= LEVEL_INSTANCE))
     {
-      result = IOD_EC_InvalidElementValue;
+        if (!m_SOPInstanceUID.empty())
+        {
+            result = DcmUniqueIdentifier::checkStringValue(m_SOPInstanceUID, "1");
+        }
+        else
+        {
+            result = IOD_EC_InvalidElementValue;
+        }
     }
-  }
-  return result;
+    return result;
 }
 
-
 IODReference* IODReference::clone() const
 {
-  IODReference* ref = new IODReference();
-  if (ref)
-  {
-    ref->m_PatientID = m_PatientID;
-    ref->m_StudyInstanceUID = m_StudyInstanceUID;
-    ref->m_SeriesInstanceUID = m_SeriesInstanceUID;
-    ref->m_SOPClassUID = m_SOPClassUID;
-    ref->m_SOPInstanceUID = m_SOPInstanceUID;
-    ref->m_Level = m_Level;
-  }
-  return ref;
+    IODReference* ref = new IODReference();
+    if (ref)
+    {
+        ref->m_PatientID         = m_PatientID;
+        ref->m_StudyInstanceUID  = m_StudyInstanceUID;
+        ref->m_SeriesInstanceUID = m_SeriesInstanceUID;
+        ref->m_SOPClassUID       = m_SOPClassUID;
+        ref->m_SOPInstanceUID    = m_SOPInstanceUID;
+        ref->m_Level             = m_Level;
+    }
+    return ref;
 }
 
-
 // ------------------- class IODImageReference -------------------------------
 
-
 IODImageReference::IODImageReference(const IODReference::MAX_LEVEL level)
-: IODReference(level),
-  m_ReferencedFrameNumber()
+    : IODReference(level)
+    , m_ReferencedFrameNumber()
 {
 }
 
 IODImageReference::IODImageReference()
-: IODReference(LEVEL_INSTANCE),
-  m_ReferencedFrameNumber()
+    : IODReference(LEVEL_INSTANCE)
+    , m_ReferencedFrameNumber()
 {
-
 }
 
-
 IODImageReference::IODImageReference(const OFString& patientID,
                                      const OFString& studyUID,
                                      const OFString& seriesUID,
                                      const OFString& sopInstanceUID,
                                      const OFString& sopClassUID,
                                      const OFVector<Uint32>& refFrameNumbers)
-: IODReference(LEVEL_INSTANCE),
-  m_ReferencedFrameNumber(refFrameNumbers)
+    : IODReference(LEVEL_INSTANCE)
+    , m_ReferencedFrameNumber(refFrameNumbers)
 {
-  m_PatientID = patientID;
-  m_StudyInstanceUID = studyUID;
-  m_SeriesInstanceUID = seriesUID;
-  m_SOPInstanceUID = sopInstanceUID;
-  m_SOPClassUID = sopClassUID;
+    m_PatientID         = patientID;
+    m_StudyInstanceUID  = studyUID;
+    m_SeriesInstanceUID = seriesUID;
+    m_SOPInstanceUID    = sopInstanceUID;
+    m_SOPClassUID       = sopClassUID;
 }
 
-
 IODImageReference::IODImageReference(const OFString& patientID,
                                      const OFString& studyUID,
                                      const OFString& seriesUID,
                                      const OFString& sopInstanceUID,
                                      const OFString& sopClassUID)
-: m_ReferencedFrameNumber()
+    : m_ReferencedFrameNumber()
 {
-  m_PatientID = patientID;
-  m_StudyInstanceUID = studyUID;
-  m_SeriesInstanceUID = seriesUID;
-  m_SOPInstanceUID = sopInstanceUID;
-  m_SOPClassUID = sopClassUID;
+    m_PatientID         = patientID;
+    m_StudyInstanceUID  = studyUID;
+    m_SeriesInstanceUID = seriesUID;
+    m_SOPInstanceUID    = sopInstanceUID;
+    m_SOPClassUID       = sopClassUID;
 }
 
-
-
 IODReference* IODImageReference::clone() const
 {
-  IODImageReference* ref = new IODImageReference(m_Level);
-  if (ref)
-  {
-    *(OFstatic_cast(IODReference*, ref)) = *this;
-    ref->m_ReferencedFrameNumber = m_ReferencedFrameNumber;
-  }
-  return ref;
+    IODImageReference* ref = new IODImageReference(m_Level);
+    if (ref)
+    {
+        *(OFstatic_cast(IODReference*, ref)) = *this;
+        ref->m_ReferencedFrameNumber         = m_ReferencedFrameNumber;
+    }
+    return ref;
 }
 
-
 void IODImageReference::clear()
 {
-  IODReference::clear();
-  m_ReferencedFrameNumber.clear();
+    IODReference::clear();
+    m_ReferencedFrameNumber.clear();
 }
 
-
-OFBool IODImageReference::readFromFile(const OFString& filename,
-                                       const OFVector< Uint32 > frameNumbers)
+OFBool IODImageReference::readFromFile(const OFString& filename, const OFVector<Uint32> frameNumbers)
 {
-  clear();
-  DcmFileFormat ff;
-  OFCondition result = ff.loadFile(filename.c_str());
-  if (result.good())
-  {
-    if ( readFromItem( *ff.getDataset() ) )
+    clear();
+    DcmFileFormat ff;
+    OFCondition result = ff.loadFile(filename.c_str());
+    if (result.good())
     {
-      m_ReferencedFrameNumber = frameNumbers;
-      return OFTrue;
+        if (readFromItem(*ff.getDataset()))
+        {
+            m_ReferencedFrameNumber = frameNumbers;
+            return OFTrue;
+        }
     }
-  }
-  return OFFalse;
+    return OFFalse;
 }
 
-
 // ------------------ class IODSegmentationReference ---------------------------
 
 IODSegmentationReference::IODSegmentationReference(const IODReference::MAX_LEVEL level)
-: IODReference(level),
-  m_ReferencedSegmentNumber()
+    : IODReference(level)
+    , m_ReferencedSegmentNumber()
 {
 }
 
-
 IODSegmentationReference::IODSegmentationReference()
-: IODReference(LEVEL_INSTANCE),
-  m_ReferencedSegmentNumber()
+    : IODReference(LEVEL_INSTANCE)
+    , m_ReferencedSegmentNumber()
 {
-
 }
 
-
 IODReference* IODSegmentationReference::clone() const
 {
-  IODSegmentationReference* ref = new IODSegmentationReference(m_Level);
-  if (ref)
-  {
-    *(OFstatic_cast(IODReference*, ref)) = *this;
-    ref->m_ReferencedSegmentNumber = m_ReferencedSegmentNumber;
-  }
-  return ref;
+    IODSegmentationReference* ref = new IODSegmentationReference(m_Level);
+    if (ref)
+    {
+        *(OFstatic_cast(IODReference*, ref)) = *this;
+        ref->m_ReferencedSegmentNumber       = m_ReferencedSegmentNumber;
+    }
+    return ref;
 }
 
-
-OFBool IODSegmentationReference::readFromFile(const OFString& filename,
-                                              const OFVector< Uint16 > segmentNumbers)
+OFBool IODSegmentationReference::readFromFile(const OFString& filename, const OFVector<Uint16> segmentNumbers)
 {
-  clear();
-  DcmFileFormat ff;
-  OFCondition result = ff.loadFile(filename.c_str());
-  if (result.good())
-  {
-    if ( readFromItem(*ff.getDataset()) )
+    clear();
+    DcmFileFormat ff;
+    OFCondition result = ff.loadFile(filename.c_str());
+    if (result.good())
     {
-      m_ReferencedSegmentNumber = segmentNumbers;
-      return OFTrue;
+        if (readFromItem(*ff.getDataset()))
+        {
+            m_ReferencedSegmentNumber = segmentNumbers;
+            return OFTrue;
+        }
     }
-  }
-  return OFFalse;
+    return OFFalse;
 }
 
-
 void IODSegmentationReference::clear()
 {
-  IODReference::clear();
-  m_ReferencedSegmentNumber.clear();
+    IODReference::clear();
+    m_ReferencedSegmentNumber.clear();
 }
 
-
-
 IODReferences::IODReferences()
-: m_References()
+    : m_References()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
 IODReferences::~IODReferences()
 {
-  DcmIODUtil::freeContainer(m_References);
+    DcmIODUtil::freeContainer(m_References);
 }
 
-
 IODReferences::IODReferences(const IODReferences& rhs)
-: m_References()
+    : m_References()
 {
-  *this = rhs;
+    *this = rhs;
 }
 
-
-IODReferences & IODReferences::operator=(const IODReferences& rhs)
+IODReferences& IODReferences::operator=(const IODReferences& rhs)
 {
-  if (&rhs == this)
-    return *this;
+    if (&rhs == this)
+        return *this;
 
-  OFVector<IODReference*>::const_iterator ref = rhs.m_References.begin();
-  while (ref != rhs.m_References.end())
-  {
-    m_References.push_back( (*ref)->clone());
-    ref++;
-  }
-  return *this;
+    OFVector<IODReference*>::const_iterator ref = rhs.m_References.begin();
+    while (ref != rhs.m_References.end())
+    {
+        m_References.push_back((*ref)->clone());
+        ref++;
+    }
+    return *this;
 }
 
-
-
 const OFVector<IODReference*>& IODReferences::get() const
 {
-  return m_References;
+    return m_References;
 }
 
-
 size_t IODReferences::size() const
 {
-  return m_References.size();
+    return m_References.size();
 }
 
-
-size_t IODReferences::addFromFiles(const OFVector< OFString >& dcmFiles,
-                                   const IODReference::MAX_LEVEL level)
+size_t IODReferences::addFromFiles(const OFVector<OFString>& dcmFiles, const IODReference::MAX_LEVEL level)
 {
-  if (dcmFiles.empty())
-  {
-    return 0;
-  }
-
-  OFCondition result;
-  OFVector<OFString>::const_iterator it = dcmFiles.begin();
-  size_t count = 0;
-  while (it != dcmFiles.end())
-  {
-    IODReference* ref = new IODReference(level);
-    if (ref && ref->readFromFile(*it))
+    if (dcmFiles.empty())
     {
-      m_References.push_back(ref);
-      count++;
+        return 0;
     }
-    else
+
+    OFCondition result;
+    OFVector<OFString>::const_iterator it = dcmFiles.begin();
+    size_t count                          = 0;
+    while (it != dcmFiles.end())
     {
-      DCMIOD_WARN("Could not add references from file " << (*it) << " (skipping)");
-      delete ref;
+        IODReference* ref = new IODReference(level);
+        if (ref && ref->readFromFile(*it))
+        {
+            m_References.push_back(ref);
+            count++;
+        }
+        else
+        {
+            DCMIOD_WARN("Could not add references from file " << (*it) << " (skipping)");
+            delete ref;
+        }
+        it++;
     }
-    it++;
-  }
-  return count;
+    return count;
 }
 
-
 void IODReferences::clearData()
 {
-  DcmIODUtil::freeContainer(m_References);
+    DcmIODUtil::freeContainer(m_References);
 }
index d9df261c1211796a7dd62de8c238d8966e64986e..86740fa8dea21d3bf9ecf3d39275715a59384821 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"
 #include "dcmtk/dcmiod/iodrules.h"
-#include "dcmtk/dcmiod/iodtypes.h"
-#include "dcmtk/dcmdata/dcitem.h"
+#include "dcmtk/config/osconfig.h"
 #include "dcmtk/dcmdata/dcelem.h"
+#include "dcmtk/dcmdata/dcitem.h"
 #include "dcmtk/dcmdata/dctagkey.h"
+#include "dcmtk/dcmiod/iodtypes.h"
 
-
-IODRules::IODRules() :
-m_Rules()
+IODRules::IODRules()
+    : m_Rules()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
 IODRules* IODRules::clone()
 {
-  IODRules *newRules = new IODRules();
-  if (newRules)
-  {
-    OFMap<DcmTagKey, IODRule*>::iterator it = m_Rules.begin();
-    while (it != m_Rules.end())
+    IODRules* newRules = new IODRules();
+    if (newRules)
     {
-      if (it->second)
-      {
-        IODRule* newRule = it->second->clone();
-        if (newRule)
-        {
-           newRules->addRule(newRule);
-        }
-        else
+        OFMap<DcmTagKey, IODRule*>::iterator it = m_Rules.begin();
+        while (it != m_Rules.end())
         {
-          DCMIOD_WARN("Cannot create new IODRule, memory exhausted?");
+            if (it->second)
+            {
+                IODRule* newRule = it->second->clone();
+                if (newRule)
+                {
+                    newRules->addRule(newRule);
+                }
+                else
+                {
+                    DCMIOD_WARN("Cannot create new IODRule, memory exhausted?");
+                }
+            }
+            else
+            {
+                DCMIOD_WARN("Found NULL IODRule, cannot clone");
+            }
+            it++;
         }
-      }
-      else
-      {
-        DCMIOD_WARN("Found NULL IODRule, cannot clone");
-      }
-      it++;
     }
-  }
-  else
-  {
-    DCMIOD_WARN("Cannot create new IODRules, memory exhausted?");
-  }
-  return newRules;
+    else
+    {
+        DCMIOD_WARN("Cannot create new IODRules, memory exhausted?");
+    }
+    return newRules;
 }
 
-
 IODRule* IODRules::getByTag(const DcmTagKey& key) const
 {
-  IODRules::const_iterator it = m_Rules.find(key);
-  if ( it != m_Rules.end() )
-    return (*it).second;
-  else
-    return NULL;
+    IODRules::const_iterator it = m_Rules.find(key);
+    if (it != m_Rules.end())
+        return (*it).second;
+    else
+        return NULL;
 }
 
-
 IODRules::iterator IODRules::begin()
 {
-  return m_Rules.begin();
+    return m_Rules.begin();
 }
 
 IODRules::iterator IODRules::end()
 {
-  return m_Rules.end();
+    return m_Rules.end();
 }
 
-
 void IODRules::clear()
 {
 
-  while (m_Rules.size() > 0)
-  {
-    IODRules::iterator it = m_Rules.begin();
-    IODRule* rule = (*it).second;
-    m_Rules.erase(it);
-    delete rule;
-    rule = NULL;
-  }
+    while (m_Rules.size() > 0)
+    {
+        IODRules::iterator it = m_Rules.begin();
+        IODRule* rule         = (*it).second;
+        m_Rules.erase(it);
+        delete rule;
+        rule = NULL;
+    }
 }
 
-OFBool IODRules::addRule(IODRule* rule,
-                         const OFBool overwriteExisting)
+OFBool IODRules::addRule(IODRule* rule, const OFBool overwriteExisting)
 {
-  if (rule == NULL)
-  {
-    DCMIOD_ERROR("Cannot add IOD rule: NULL pointer");
-    return OFFalse;
-  }
-  DcmTagKey key = rule->getTagKey();
-  iterator it = m_Rules.find(key);
-  if ( it != m_Rules.end() )
-  {
-    if (overwriteExisting)
+    if (rule == NULL)
     {
-      delete (*it).second;
-      (*it).second = rule;
+        DCMIOD_ERROR("Cannot add IOD rule: NULL pointer");
+        return OFFalse;
+    }
+    DcmTagKey key = rule->getTagKey();
+    iterator it   = m_Rules.find(key);
+    if (it != m_Rules.end())
+    {
+        if (overwriteExisting)
+        {
+            delete (*it).second;
+            (*it).second = rule;
+        }
+        else
+        {
+            DCMIOD_DEBUG("IOD rule for tag " << key << " not inserted (already existing and overwriting disabled)");
+            return OFFalse;
+        }
     }
     else
     {
-      DCMIOD_DEBUG("IOD rule for tag " << key << " not inserted (already existing and overwriting disabled)");
-      return OFFalse;
+        m_Rules.insert(OFMake_pair(key, rule));
     }
-  }
-  else
-  {
-    m_Rules.insert( OFMake_pair ( key, rule) );
-  }
-  return OFTrue;
+    return OFTrue;
 }
 
-
-const OFVector< IODRule* > IODRules::getByModule(const OFString& moduleName)
+const OFVector<IODRule*> IODRules::getByModule(const OFString& moduleName)
 {
-  OFVector<IODRule*> result;
-  IODRules::iterator it = m_Rules.begin();
-  while (it != m_Rules.end())
-  {
-    if ( (*it).second->getModule() == moduleName )
+    OFVector<IODRule*> result;
+    IODRules::iterator it = m_Rules.begin();
+    while (it != m_Rules.end())
     {
-      result.push_back((*it).second);
+        if ((*it).second->getModule() == moduleName)
+        {
+            result.push_back((*it).second);
+        }
+        it++;
     }
-    it++;
-  }
-  return result;
+    return result;
 }
 
-
 OFBool IODRules::deleteRule(const DcmTagKey key)
 {
-  IODRules::iterator it = m_Rules.find(key);
-  if ( it != m_Rules.end() )
-  {
-    IODRule* rule = (*it).second;
-    m_Rules.erase(it);
-    delete rule;
-    return OFTrue;
-  }
-  return OFFalse;
+    IODRules::iterator it = m_Rules.find(key);
+    if (it != m_Rules.end())
+    {
+        IODRule* rule = (*it).second;
+        m_Rules.erase(it);
+        delete rule;
+        return OFTrue;
+    }
+    return OFFalse;
 }
 
-
-void IODRules::dump(STD_NAMESPACE ostream &out)
+void IODRules::dump(STD_NAMESPACE ostream& out)
 {
-  IODRules::iterator it = m_Rules.begin();
-  while ( it != m_Rules.end() )
-  {
-    out << (*it).first << ": Type \"" << (*it).second->getType() << "\", VM \"" << (*it).second->getType() << "\"" << OFendl;
-    it++;
-  }
+    IODRules::iterator it = m_Rules.begin();
+    while (it != m_Rules.end())
+    {
+        out << (*it).first << ": Type \"" << (*it).second->getType() << "\", VM \"" << (*it).second->getType() << "\""
+            << OFendl;
+        it++;
+    }
 }
 
-
 IODRules::~IODRules()
 {
-  clear();
+    clear();
 }
 
-
-
 IODRule::IODRule(const DcmTagKey& key,
                  const OFString& VM,
                  const OFString& type,
@@ -189,176 +178,167 @@ IODRule::IODRule(const DcmTagKey& key,
                  const DcmIODTypes::IOD_IE ie,
                  const OFString& defaultValue,
                  const OFString& privateCreator)
-: m_Key(key),
-m_VM(VM),
-m_Type(type),
-m_Module(module),
-m_IE(ie),
-m_DefaultValue(defaultValue),
-m_PrivateCreator(privateCreator)
+    : m_Key(key)
+    , m_VM(VM)
+    , m_Type(type)
+    , m_Module(module)
+    , m_IE(ie)
+    , m_DefaultValue(defaultValue)
+    , m_PrivateCreator(privateCreator)
 {
-  // nothing else to do
+    // nothing else to do
 }
 
-
 IODRule::~IODRule()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
 IODRule* IODRule::clone()
 {
-  return new IODRule(m_Key, m_VM, m_Type, m_Module, m_IE, m_DefaultValue, m_PrivateCreator);
+    return new IODRule(m_Key, m_VM, m_Type, m_Module, m_IE, m_DefaultValue, m_PrivateCreator);
 }
 
-
-
 OFString IODRule::getPrivateCreator() const
 {
-  return m_PrivateCreator;
+    return m_PrivateCreator;
 }
 
-
 DcmTagKey IODRule::getTagKey() const
 {
-  return m_Key;
+    return m_Key;
 }
 
-
-
 OFString IODRule::getModule() const
 {
-  return m_Module;
+    return m_Module;
 }
 
-
 OFString IODRule::getType() const
 {
-  return m_Type;
+    return m_Type;
 }
 
-
 OFString IODRule::getVM() const
 {
-  return m_VM;
+    return m_VM;
 }
 
-
 OFString IODRule::getDefaultValue() const
 {
-  return m_DefaultValue;
+    return m_DefaultValue;
 }
 
-
-DcmIODTypes::IOD_IE  IODRule::getIE() const
+DcmIODTypes::IOD_IE IODRule::getIE() const
 {
-  return m_IE;
+    return m_IE;
 }
 
-
 OFBool IODRule::setType(const OFString& val)
 {
-  if ( (val != "1") && (val != "1C") && (val != "2") && (val != "2C") && (val != "3") )
-  {
-    return OFFalse;
-  }
-  m_Type = val;
-  return OFTrue;
+    if ((val != "1") && (val != "1C") && (val != "2") && (val != "2C") && (val != "3"))
+    {
+        return OFFalse;
+    }
+    m_Type = val;
+    return OFTrue;
 }
 
-
 OFBool IODRule::setModule(const OFString& val)
 {
-  if (val.empty())
-  {
-    return OFFalse;
-  }
-  m_Module = val;
-  return OFTrue;
+    if (val.empty())
+    {
+        return OFFalse;
+    }
+    m_Module = val;
+    return OFTrue;
 }
 
-
-
 OFBool IODRule::setPrivateCreator(const OFString& val)
 {
-  if (val.empty())
-  {
-    return OFFalse;
-  }
-  m_PrivateCreator = val;
-  return OFTrue;
+    if (val.empty())
+    {
+        return OFFalse;
+    }
+    m_PrivateCreator = val;
+    return OFTrue;
 }
 
-
 OFBool IODRule::setDefaultValue(const OFString& val)
 {
-  if (val.empty())
-  {
-    return OFFalse;
-  }
-  m_DefaultValue = val;
-  return OFTrue;
+    if (val.empty())
+    {
+        return OFFalse;
+    }
+    m_DefaultValue = val;
+    return OFTrue;
 }
 
-
 OFBool IODRule::setVM(const OFString& val)
 {
-  // One could check whether this is a valid VM string...
-  m_VM = val;
-  return OFTrue;
+    // One could check whether this is a valid VM string...
+    m_VM = val;
+    return OFTrue;
 }
 
-
-OFCondition IODRule::check(DcmItem& item,
-                           const OFBool quiet)
+OFCondition IODRule::check(DcmItem& item, const OFBool quiet)
 {
-  OFCondition result;
-  const OFString tagName = DcmTag(m_Key).getTagName();
-  DcmElement *elem = NULL;
-  OFCondition searchCond = item.findAndGetElement(m_Key, elem, OFFalse /* only this level */);
-  /* NB: type 1C and 2C cannot be checked, assuming to be optional */
-  if (((m_Type == "1") || (m_Type== "2")) && searchCond.bad())
-  {
-    if (!quiet) DCMIOD_WARN(tagName << " " << m_Key << " absent in " << m_Module << " (type " << m_Type << ")");
-    result = EC_MissingAttribute;
-  }
-  else if ((elem == NULL) || elem->isEmpty(OFTrue /*normalize*/))
-  {
-    /* however, type 1C should never be present with empty value */
-    if (((m_Type == "1") || (m_Type == "1C")) && searchCond.good())
+    OFCondition result;
+    const OFString tagName = DcmTag(m_Key).getTagName();
+    DcmElement* elem       = NULL;
+    OFCondition searchCond = item.findAndGetElement(m_Key, elem, OFFalse /* only this level */);
+    /* NB: type 1C and 2C cannot be checked, assuming to be optional */
+    if (((m_Type == "1") || (m_Type == "2")) && searchCond.bad())
     {
-      if (!quiet) DCMIOD_WARN(tagName << " " << m_Key << " empty in " << m_Module << " (type " << m_Type << ")");
-      result = EC_MissingValue;
+        if (!quiet)
+            DCMIOD_WARN(tagName << " " << m_Key << " absent in " << m_Module << " (type " << m_Type << ")");
+        result = EC_MissingAttribute;
     }
-  } else {
-    const OFCondition checkResult = elem->checkValue(m_VM, OFTrue /*oldFormat*/);
-    if (checkResult == EC_InvalidCharacter)
+    else if ((elem == NULL) || elem->isEmpty(OFTrue /*normalize*/))
     {
-      if (!quiet) DCMIOD_WARN(tagName << " " << m_Key << " contains invalid character(s) in " << m_Module);
-      result = checkResult;
-    }
-    else if (checkResult == EC_ValueRepresentationViolated)
-    {
-      if (!quiet) DCMIOD_WARN(tagName << " " << m_Key << " violates VR definition in " << m_Module);
-      result = checkResult;
-    }
-    else if (checkResult == EC_ValueMultiplicityViolated)
-    {
-      const OFString vmText = (elem->getVR() == EVR_SQ) ? " #items" : " VM";
-      if (!quiet) DCMIOD_WARN(tagName << " " << m_Key << vmText << " != " << m_VM << " in " << m_Module);
-      result = checkResult;
-    }
-    else if (checkResult == EC_MaximumLengthViolated)
-    {
-      if (!quiet) DCMIOD_WARN(tagName << " " << m_Key << " violates maximum VR length in " << m_Module);
-      result = checkResult;
+        /* however, type 1C should never be present with empty value */
+        if (((m_Type == "1") || (m_Type == "1C")) && searchCond.good())
+        {
+            if (!quiet)
+                DCMIOD_WARN(tagName << " " << m_Key << " empty in " << m_Module << " (type " << m_Type << ")");
+            result = EC_MissingValue;
+        }
     }
-    else if (checkResult.bad())
+    else
     {
-      if (!quiet) DCMIOD_DEBUG("INTERNAL ERROR while checking value of " << tagName << " " << m_Key << " in " << m_Module);
-      result = EC_InternalError;
+        const OFCondition checkResult = elem->checkValue(m_VM, OFTrue /*oldFormat*/);
+        if (checkResult == EC_InvalidCharacter)
+        {
+            if (!quiet)
+                DCMIOD_WARN(tagName << " " << m_Key << " contains invalid character(s) in " << m_Module);
+            result = checkResult;
+        }
+        else if (checkResult == EC_ValueRepresentationViolated)
+        {
+            if (!quiet)
+                DCMIOD_WARN(tagName << " " << m_Key << " violates VR definition in " << m_Module);
+            result = checkResult;
+        }
+        else if (checkResult == EC_ValueMultiplicityViolated)
+        {
+            const OFString vmText = (elem->getVR() == EVR_SQ) ? " #items" : " VM";
+            if (!quiet)
+                DCMIOD_WARN(tagName << " " << m_Key << vmText << " != " << m_VM << " in " << m_Module);
+            result = checkResult;
+        }
+        else if (checkResult == EC_MaximumLengthViolated)
+        {
+            if (!quiet)
+                DCMIOD_WARN(tagName << " " << m_Key << " violates maximum VR length in " << m_Module);
+            result = checkResult;
+        }
+        else if (checkResult.bad())
+        {
+            if (!quiet)
+                DCMIOD_DEBUG("INTERNAL ERROR while checking value of " << tagName << " " << m_Key << " in "
+                                                                       << m_Module);
+            result = EC_InternalError;
+        }
     }
-  }
-  return result;
+    return result;
 }
index 74dc4d9e78965d2a2cb31e85489bb38d2ac8404d..9ea5fce8c0a992f2c665caea4d60330b3c5e4781 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"
 #include "dcmtk/dcmiod/iodtypes.h"
+#include "dcmtk/config/osconfig.h"
 #include "dcmtk/dcmdata/dcerror.h"
 
 OFLogger DCM_dcmiodLogger = OFLog::getLogger("dcmtk.dcmiod");
 
-
 /*---------------------------------*
  *  constant definitions
  *---------------------------------*/
 
 // conditions
-makeOFConditionConst(IOD_EC_WrongSOPClass,         OFM_dcmiod,  1, OF_error, "Wrong SOP Class");
-makeOFConditionConst(IOD_EC_MissingAttribute,      OFM_dcmiod,  2, OF_error, "Missing Attribute(s)");
-makeOFConditionConst(IOD_EC_MissingSequenceData,   OFM_dcmiod,  3, OF_error, "Missing Sequence Data");
-makeOFConditionConst(IOD_EC_InvalidDimensions,     OFM_dcmiod,  4, OF_error, "Invalid dimension information");
-makeOFConditionConst(IOD_EC_CannotInsertFrame,     OFM_dcmiod,  5, OF_error, "Cannot insert frame");
-makeOFConditionConst(IOD_EC_InvalidPixelData,      OFM_dcmiod,  6, OF_error, "Invalid Pixel Data");
-makeOFConditionConst(IOD_EC_InvalidObject,         OFM_dcmiod,  7, OF_error, "Invalid Object");
-makeOFConditionConst(IOD_EC_CannotDecompress,      OFM_dcmiod,  8, OF_error, "Cannot decompress");
-makeOFConditionConst(IOD_EC_NoSuchRule,            OFM_dcmiod,  9, OF_error, "No such IOD rule");
-makeOFConditionConst(IOD_EC_InvalidLaterality,     OFM_dcmiod, 10, OF_error, "Invalid value for 'Laterality' (only 'L' or 'R' permitted)");
-makeOFConditionConst(IOD_EC_InvalidElementValue,   OFM_dcmiod, 11, OF_error, "Value not allowed for element");
-makeOFConditionConst(IOD_EC_InvalidReference,      OFM_dcmiod, 12, OF_error, "One or more invalid SOP references");
-makeOFConditionConst(IOD_EC_ReferencesOmitted,     OFM_dcmiod, 13, OF_error, "One or more SOP references have been omitted");
+makeOFConditionConst(IOD_EC_WrongSOPClass, OFM_dcmiod, 1, OF_error, "Wrong SOP Class");
+makeOFConditionConst(IOD_EC_MissingAttribute, OFM_dcmiod, 2, OF_error, "Missing Attribute(s)");
+makeOFConditionConst(IOD_EC_MissingSequenceData, OFM_dcmiod, 3, OF_error, "Missing Sequence Data");
+makeOFConditionConst(IOD_EC_InvalidDimensions, OFM_dcmiod, 4, OF_error, "Invalid dimension information");
+makeOFConditionConst(IOD_EC_CannotInsertFrame, OFM_dcmiod, 5, OF_error, "Cannot insert frame");
+makeOFConditionConst(IOD_EC_InvalidPixelData, OFM_dcmiod, 6, OF_error, "Invalid Pixel Data");
+makeOFConditionConst(IOD_EC_InvalidObject, OFM_dcmiod, 7, OF_error, "Invalid Object");
+makeOFConditionConst(IOD_EC_CannotDecompress, OFM_dcmiod, 8, OF_error, "Cannot decompress");
+makeOFConditionConst(IOD_EC_NoSuchRule, OFM_dcmiod, 9, OF_error, "No such IOD rule");
+makeOFConditionConst(
+    IOD_EC_InvalidLaterality, OFM_dcmiod, 10, OF_error, "Invalid value for 'Laterality' (only 'L' or 'R' permitted)");
+makeOFConditionConst(IOD_EC_InvalidElementValue, OFM_dcmiod, 11, OF_error, "Value not allowed for element");
+makeOFConditionConst(IOD_EC_InvalidReference, OFM_dcmiod, 12, OF_error, "One or more invalid SOP references");
+makeOFConditionConst(
+    IOD_EC_ReferencesOmitted, OFM_dcmiod, 13, OF_error, "One or more SOP references have been omitted");
index b951f8aaa6f36c87feaf6c8bbc1ff96b642a65e8..c06680ce89d3c3f2ed699612bea1355ce57b48e3 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
-#include "dcmtk/dcmdata/dctypes.h"    // logger
 #include "dcmtk/dcmiod/iodutil.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+#include "dcmtk/dcmdata/dctypes.h" // logger
 #include "dcmtk/dcmiod/iodrules.h"
 
-#include "dcmtk/dcmdata/dcmetinf.h"
 #include "dcmtk/dcmdata/dcdeftag.h"
-#include "dcmtk/dcmdata/dcdict.h"
 #include "dcmtk/dcmdata/dcdicent.h"
-#include "dcmtk/dcmdata/dcsequen.h"
+#include "dcmtk/dcmdata/dcdict.h"
 #include "dcmtk/dcmdata/dcfilefo.h"
+#include "dcmtk/dcmdata/dcitem.h"
+#include "dcmtk/dcmdata/dcmetinf.h"
+#include "dcmtk/dcmdata/dcsequen.h"
+#include "dcmtk/dcmdata/dcuid.h"
 #include "dcmtk/dcmdata/dcvrda.h"
 #include "dcmtk/dcmdata/dcvrtm.h"
-#include "dcmtk/dcmdata/dcuid.h"
-#include "dcmtk/dcmdata/dcitem.h"
-
 
 // --- static helpers ---
 
-OFCondition DcmIODUtil::getAndCheckElementFromDataset(DcmItem &dataset,
-                                                      DcmElement &delem,
-                                                      const OFString &vm,
-                                                      const OFString &type,
-                                                      const char *moduleName)
-{
-  DcmStack stack;
-  const DcmTagKey tagKey = delem.getTag();
-  OFCondition result = dataset.search(tagKey, stack, ESM_fromHere, OFFalse /*searchIntoSub*/);
-  if (result.good())
-  {
-    /* copy object from search stack */
-    result = delem.copyFrom(*stack.top());
-    /* we need a reference to the original element in order to determine the SpecificCharacterSet */
-    checkElementValue(OFstatic_cast(DcmElement *, stack.top()), tagKey, vm, type, result, moduleName, dcmtk::log4cplus::WARN_LOG_LEVEL);
-  }
-  /* the element could not be found in the dataset */
-  else
-  {
-    checkElementValue(delem, vm, type, result, moduleName, dcmtk::log4cplus::WARN_LOG_LEVEL);
-  }
-  return result;
-}
-
-
-OFCondition DcmIODUtil::getAndCheckElementFromDataset(DcmItem &dataset,
+OFCondition DcmIODUtil::getAndCheckElementFromDataset(
+    DcmItem& dataset, DcmElement& delem, const OFString& vm, const OFString& type, const char* moduleName)
+{
+    DcmStack stack;
+    const DcmTagKey tagKey = delem.getTag();
+    OFCondition result     = dataset.search(tagKey, stack, ESM_fromHere, OFFalse /*searchIntoSub*/);
+    if (result.good())
+    {
+        /* copy object from search stack */
+        result = delem.copyFrom(*stack.top());
+        /* we need a reference to the original element in order to determine the SpecificCharacterSet */
+        checkElementValue(OFstatic_cast(DcmElement*, stack.top()),
+                          tagKey,
+                          vm,
+                          type,
+                          result,
+                          moduleName,
+                          dcmtk::log4cplus::WARN_LOG_LEVEL);
+    }
+    /* the element could not be found in the dataset */
+    else
+    {
+        checkElementValue(delem, vm, type, result, moduleName, dcmtk::log4cplus::WARN_LOG_LEVEL);
+    }
+    return result;
+}
+
+OFCondition DcmIODUtil::getAndCheckElementFromDataset(DcmItem& dataset,
                                                       const DcmTagKey& tagKey,
                                                       DcmElement*& delem,
-                                                      const OFString &vm,
-                                                      const OFString &type,
-                                                      const char *moduleName)
+                                                      const OFStringvm,
+                                                      const OFStringtype,
+                                                      const charmoduleName)
 {
-  if (delem)
-    return EC_IllegalParameter;
+    if (delem)
+        return EC_IllegalParameter;
 
-  DcmStack stack;
-  OFCondition result = dataset.search(tagKey, stack, ESM_fromHere, OFFalse /*searchIntoSub*/);
-  if (result.good())
-  {
-    /* copy object from search stack */
-    delem = OFstatic_cast ( DcmElement*, stack.top()->clone() );
-    /* we need a reference to the original element in order to determine the SpecificCharacterSet */
-    checkElementValue(OFstatic_cast(DcmElement *, stack.top()), tagKey, vm, type, result, moduleName, dcmtk::log4cplus::WARN_LOG_LEVEL);
-  }
-  /* the element could not be found in the dataset */
-  else
-    checkElementValue(delem, tagKey, vm, type, result, moduleName, dcmtk::log4cplus::WARN_LOG_LEVEL);
+    DcmStack stack;
+    OFCondition result = dataset.search(tagKey, stack, ESM_fromHere, OFFalse /*searchIntoSub*/);
+    if (result.good())
+    {
+        /* copy object from search stack */
+        delem = OFstatic_cast(DcmElement*, stack.top()->clone());
+        /* we need a reference to the original element in order to determine the SpecificCharacterSet */
+        checkElementValue(OFstatic_cast(DcmElement*, stack.top()),
+                          tagKey,
+                          vm,
+                          type,
+                          result,
+                          moduleName,
+                          dcmtk::log4cplus::WARN_LOG_LEVEL);
+    }
+    /* the element could not be found in the dataset */
+    else
+        checkElementValue(delem, tagKey, vm, type, result, moduleName, dcmtk::log4cplus::WARN_LOG_LEVEL);
 
-  return result;
+    return result;
 }
 
-
-
-OFCondition DcmIODUtil::getAndCheckElementFromDataset(DcmItem &dataset,
-                                                      DcmElement &delem,
-                                                      const IODRule* rule)
+OFCondition DcmIODUtil::getAndCheckElementFromDataset(DcmItem& dataset, DcmElement& delem, const IODRule* rule)
 {
-  if (rule == NULL)
-    return EC_CannotCheck;
+    if (rule == NULL)
+        return EC_CannotCheck;
 
-  return getAndCheckElementFromDataset(dataset, delem, rule->getVM(), rule->getType(), rule->getModule().c_str());
+    return getAndCheckElementFromDataset(dataset, delem, rule->getVM(), rule->getType(), rule->getModule().c_str());
 }
 
-
-OFCondition DcmIODUtil::getAndCheckElementFromDataset(DcmItem &dataset,
-                                                      DcmElement*& delem,
-                                                      const IODRule* rule)
+OFCondition DcmIODUtil::getAndCheckElementFromDataset(DcmItem& dataset, DcmElement*& delem, const IODRule* rule)
 {
-  if (rule == NULL)
-    return EC_CannotCheck;
+    if (rule == NULL)
+        return EC_CannotCheck;
 
-  return getAndCheckElementFromDataset(dataset, rule->getTagKey(), delem, rule->getVM(), rule->getType(), rule->getModule().c_str());
+    return getAndCheckElementFromDataset(
+        dataset, rule->getTagKey(), delem, rule->getVM(), rule->getType(), rule->getModule().c_str());
 }
 
-
-
-OFCondition DcmIODUtil::copyElementToDataset(OFCondition &result,
-                                             DcmItem &dataset,
-                                             const DcmElement &delem,
-                                             const IODRule* rule)
+OFCondition
+DcmIODUtil::copyElementToDataset(OFCondition& result, DcmItem& dataset, const DcmElement& delem, const IODRule* rule)
 {
-  if (rule == NULL)
-    return EC_CannotCheck;
+    if (rule == NULL)
+        return EC_CannotCheck;
 
-  if (result.bad())
-    return result;
+    if (result.bad())
+        return result;
 
-  // addElementToDataset() consumes element, so create a copy
-  DcmElement * copy = OFstatic_cast(DcmElement*, delem.clone());
-  if (!copy)
-    return EC_MemoryExhausted;
+    // addElementToDataset() consumes element, so create a copy
+    DcmElement* copy = OFstatic_cast(DcmElement*, delem.clone());
+    if (!copy)
+        return EC_MemoryExhausted;
 
-  return addElementToDataset(result, dataset, copy, rule);
+    return addElementToDataset(result, dataset, copy, rule);
 }
 
-
-OFCondition DcmIODUtil::copyElementToDataset(OFCondition &result,
-                                             DcmItem &dataset,
-                                             const DcmElement &delem,
-                                             const OFString &vm,
-                                             const OFString &type,
-                                             const char *moduleName)
+OFCondition DcmIODUtil::copyElementToDataset(OFCondition& result,
+                                             DcmItem& dataset,
+                                             const DcmElement& delem,
+                                             const OFString& vm,
+                                             const OFString& type,
+                                             const char* moduleName)
 {
-  // Create temporary rule (in order to avoid code-copying)
-  IODRule rule(delem.getTag(), vm, type, moduleName, DcmIODTypes::IE_UNDEFINED);
-  return copyElementToDataset(result, dataset, delem, &rule);
+    // Create temporary rule (in order to avoid code-copying)
+    IODRule rule(delem.getTag(), vm, type, moduleName, DcmIODTypes::IE_UNDEFINED);
+    return copyElementToDataset(result, dataset, delem, &rule);
 }
 
-
-OFCondition DcmIODUtil::addElementToDataset(OFCondition &result,
-                                            DcmItem &dataset,
-                                            DcmElement *delem,
-                                            const IODRule* rule)
+OFCondition
+DcmIODUtil::addElementToDataset(OFCondition& result, DcmItem& dataset, DcmElement* delem, const IODRule* rule)
 {
-  OFBool insertionOK = OFFalse;
-  if (result.good())
-  {
-    if (rule != NULL)
+    OFBool insertionOK = OFFalse;
+    if (result.good())
     {
-      // Create empty type 2 element if required
-      OFString type = rule->getType();
-      if (delem == NULL)
-      {
-        if (type == "2")
-        {
-          delem = DcmItem::newDicomElement(rule->getTagKey());
-          if (delem == NULL)
-          {
-            result = EC_MemoryExhausted;
-            return result;
-          };
-        } else if (type != "1")
+        if (rule != NULL)
         {
-          // Not type 1 or type 2 means the is type 1C, 2C or 3. For those it is
-          // fine to not insert anything
-          return EC_Normal;
+            // Create empty type 2 element if required
+            OFString type = rule->getType();
+            if (delem == NULL)
+            {
+                if (type == "2")
+                {
+                    delem = DcmItem::newDicomElement(rule->getTagKey());
+                    if (delem == NULL)
+                    {
+                        result = EC_MemoryExhausted;
+                        return result;
+                    };
+                }
+                else if (type != "1")
+                {
+                    // Not type 1 or type 2 means the is type 1C, 2C or 3. For those it is
+                    // fine to not insert anything
+                    return EC_Normal;
+                }
+                else
+                {
+                    // type 1 is missing
+                    DCMIOD_ERROR(DcmTag(rule->getTagKey()).getTagName()
+                                 << " " << rule->getTagKey() << " absent in " << rule->getModule() << " (type "
+                                 << rule->getType() << ")");
+                    result = IOD_EC_MissingAttribute;
+                    return result;
+                }
+            }
+            // At this point, we certainly have an element. Check its value (empty ok for type 2)
+            if ((type == "2") || !delem->isEmpty())
+            {
+                // Insert non-empty element or empty "type 2" element. First, perform the insertion, and then
+                // check the value. This is (at least) required for checking the character set of string values which
+                // relies on the element context, i.e. the surrounding item or dataset.
+                result = dataset.insert(delem, OFTrue /*replaceOld*/);
+                if (result.good())
+                {
+                    result = checkElementValue(*delem,
+                                               rule->getVM(),
+                                               type,
+                                               result,
+                                               rule->getModule().c_str(),
+                                               dcmtk::log4cplus::ERROR_LOG_LEVEL);
+                }
+                if (result.good())
+                {
+                    insertionOK = OFTrue;
+                }
+                // remove element if value is invalid
+                else
+                {
+                    dataset.remove(delem);
+                }
+            }
+            else if (type == "1")
+            {
+                // Empty element value not allowed for "type 1"
+                result = EC_InvalidValue;
+                checkElementValue(
+                    *delem, rule->getVM(), type, result, rule->getModule().c_str(), dcmtk::log4cplus::ERROR_LOG_LEVEL);
+            }
         }
         else
         {
-          // type 1 is missing
-          DCMIOD_ERROR(DcmTag(rule->getTagKey()).getTagName() << " " << rule->getTagKey() << " absent in " << rule->getModule() << " (type " << rule->getType() << ")");
-          result = IOD_EC_MissingAttribute;
-          return result;
+            // No rule, no checks
+            result = EC_CannotCheck;
         }
-      }
-      // At this point, we certainly have an element. Check its value (empty ok for type 2)
-      if ((type == "2") || !delem->isEmpty())
-      {
-        // Insert non-empty element or empty "type 2" element. First, perform the insertion, and then
-        // check the value. This is (at least) required for checking the character set of string values which
-        // relies on the element context, i.e. the surrounding item or dataset.
-        result = dataset.insert(delem, OFTrue /*replaceOld*/);
-        if (result.good())
-        {
-          result = checkElementValue(*delem, rule->getVM(), type, result, rule->getModule().c_str(), dcmtk::log4cplus::ERROR_LOG_LEVEL);
-        }
-        if (result.good())
-        {
-          insertionOK = OFTrue;
-        }
-        // remove element if value is invalid
-        else
-        {
-          dataset.remove(delem);
-        }
-      }
-      else if (type == "1")
-      {
-        // Empty element value not allowed for "type 1"
-        result = EC_InvalidValue;
-        checkElementValue(*delem, rule->getVM(), type, result, rule->getModule().c_str(), dcmtk::log4cplus::ERROR_LOG_LEVEL);
-      }
     }
-    else
+    if (!insertionOK)
     {
-      // No rule, no checks
-      result = EC_CannotCheck;
+        // Delete element since dataset did not take over ownership
+        delete delem;
     }
-  }
-  if (!insertionOK)
-  {
-    // Delete element since dataset did not take over ownership
-    delete delem;
-  }
 
-  return result;
+    return result;
 }
 
-
-const OFString& DcmIODUtil::currentDate(OFString &dateString)
+const OFString& DcmIODUtil::currentDate(OFString& dateString)
 {
-  if (DcmDate::getCurrentDate(dateString).bad())
-  {
-    dateString  = "";
-  }
-  return dateString;
+    if (DcmDate::getCurrentDate(dateString).bad())
+    {
+        dateString = "";
+    }
+    return dateString;
 }
 
-
-const OFString& DcmIODUtil::currentTime(OFString &timeString)
+const OFString& DcmIODUtil::currentTime(OFString& timeString)
 {
-  if (DcmTime::getCurrentTime(timeString, OFTrue /*seconds*/, OFFalse /*fraction*/).bad())
-  {
-    timeString = "";
-  }
-  return timeString;
+    if (DcmTime::getCurrentTime(timeString, OFTrue /*seconds*/, OFFalse /*fraction*/).bad())
+    {
+        timeString = "";
+    }
+    return timeString;
 }
 
-
-OFCondition DcmIODUtil::checkElementValue(const DcmElement *delem,
-                                          const DcmTagKey &tagKey,
-                                          const OFString &vm,
-                                          const OFString &type,
-                                          const OFCondition &searchCond,
-                                          const char *moduleName,
+OFCondition DcmIODUtil::checkElementValue(const DcmElement* delem,
+                                          const DcmTagKey& tagKey,
+                                          const OFString& vm,
+                                          const OFString& type,
+                                          const OFCondition& searchCond,
+                                          const char* moduleName,
                                           const dcmtk::log4cplus::LogLevel logLevel)
 {
-  OFCondition result = EC_Normal;
-  const OFString tagName = DcmTag(tagKey).getTagName();
-  const OFString module = (moduleName == NULL) ? "IOD" : moduleName;
-  OFOStringStream error;
-  /* NB: type 1C and 2C cannot be checked, assuming to be optional */
-  if (((type == "1") || (type == "2")) && searchCond.bad())
-  {
-    error << tagName << " " << tagKey << " absent in " << module << " (type " << type << ")";
-    result = IOD_EC_MissingAttribute;
-  }
-  else if ((delem == NULL) || OFconst_cast(DcmElement*, delem)->isEmpty(OFTrue /*normalize*/))   // cast away constness of delem; value modification can happen (eg. to remove padding)
-  {
-    /* however, type 1C should never be present with empty value */
-    if (((type == "1") || (type == "1C")) && searchCond.good())
-    {
-      error << tagName << " " << tagKey << " empty in " << module << " (type " << type << ")";
-      result = EC_MissingValue;
-    }
-  } else {
-    result = OFconst_cast(DcmElement*, delem)->checkValue(vm, OFTrue /*oldFormat*/);   // cast away constness of delem; value modification can happen (eg. to remove padding)
-    if (result == EC_InvalidCharacter)
+    OFCondition result     = EC_Normal;
+    const OFString tagName = DcmTag(tagKey).getTagName();
+    const OFString module  = (moduleName == NULL) ? "IOD" : moduleName;
+    OFOStringStream error;
+    /* NB: type 1C and 2C cannot be checked, assuming to be optional */
+    if (((type == "1") || (type == "2")) && searchCond.bad())
     {
-      error << tagName << " " << tagKey << " contains invalid character(s) in " << module;
+        error << tagName << " " << tagKey << " absent in " << module << " (type " << type << ")";
+        result = IOD_EC_MissingAttribute;
     }
-    else if (result == EC_ValueRepresentationViolated)
+    else if ((delem == NULL)
+             || OFconst_cast(DcmElement*, delem)
+                    ->isEmpty(OFTrue /*normalize*/)) // cast away constness of delem; value modification can happen (eg.
+                                                     // to remove padding)
     {
-      error << tagName << " " << tagKey << " violates VR definition in " << module;
-    }
-    else if (result == EC_ValueMultiplicityViolated)
-    {
-      const OFString vmText = (delem->getVR() == EVR_SQ) ? " #items" : " VM";
-      error << tagName << " " << tagKey << vmText << " != " << vm << " in " << module;
-    }
-    else if (result == EC_MaximumLengthViolated)
-    {
-      error << tagName << " " << tagKey << " violates maximum VR length in " << module;
+        /* however, type 1C should never be present with empty value */
+        if (((type == "1") || (type == "1C")) && searchCond.good())
+        {
+            error << tagName << " " << tagKey << " empty in " << module << " (type " << type << ")";
+            result = EC_MissingValue;
+        }
     }
-    else if (result.bad())
+    else
     {
-      error << "INTERNAL ERROR while checking value of " << tagName << " " << tagKey << " in " << module;
-      result = EC_Normal;
+        result = OFconst_cast(DcmElement*, delem)
+                     ->checkValue(vm, OFTrue /*oldFormat*/); // cast away constness of delem; value modification can
+                                                             // happen (eg. to remove padding)
+        if (result == EC_InvalidCharacter)
+        {
+            error << tagName << " " << tagKey << " contains invalid character(s) in " << module;
+        }
+        else if (result == EC_ValueRepresentationViolated)
+        {
+            error << tagName << " " << tagKey << " violates VR definition in " << module;
+        }
+        else if (result == EC_ValueMultiplicityViolated)
+        {
+            const OFString vmText = (delem->getVR() == EVR_SQ) ? " #items" : " VM";
+            error << tagName << " " << tagKey << vmText << " != " << vm << " in " << module;
+        }
+        else if (result == EC_MaximumLengthViolated)
+        {
+            error << tagName << " " << tagKey << " violates maximum VR length in " << module;
+        }
+        else if (result.bad())
+        {
+            error << "INTERNAL ERROR while checking value of " << tagName << " " << tagKey << " in " << module;
+            result = EC_Normal;
+        }
     }
-  }
-  OFSTRINGSTREAM_GETSTR(error, tmpString)
-  if (strlen(tmpString) > 0)
-  {
-    switch (logLevel)
+    OFSTRINGSTREAM_GETSTR(error, tmpString)
+    if (strlen(tmpString) > 0)
     {
-      case dcmtk::log4cplus::TRACE_LOG_LEVEL: DCMIOD_TRACE(tmpString); break;
-      case dcmtk::log4cplus::DEBUG_LOG_LEVEL: DCMIOD_DEBUG(tmpString); break;
-      case dcmtk::log4cplus::WARN_LOG_LEVEL : DCMIOD_WARN(tmpString); break;
-      case dcmtk::log4cplus::INFO_LOG_LEVEL : DCMIOD_INFO(tmpString); break;
-      case dcmtk::log4cplus::ERROR_LOG_LEVEL : DCMIOD_ERROR(tmpString); break;
-      case dcmtk::log4cplus::FATAL_LOG_LEVEL: DCMIOD_FATAL(tmpString); break;
-      default: DCMIOD_WARN(tmpString);;
+        switch (logLevel)
+        {
+            case dcmtk::log4cplus::TRACE_LOG_LEVEL:
+                DCMIOD_TRACE(tmpString);
+                break;
+            case dcmtk::log4cplus::DEBUG_LOG_LEVEL:
+                DCMIOD_DEBUG(tmpString);
+                break;
+            case dcmtk::log4cplus::WARN_LOG_LEVEL:
+                DCMIOD_WARN(tmpString);
+                break;
+            case dcmtk::log4cplus::INFO_LOG_LEVEL:
+                DCMIOD_INFO(tmpString);
+                break;
+            case dcmtk::log4cplus::ERROR_LOG_LEVEL:
+                DCMIOD_ERROR(tmpString);
+                break;
+            case dcmtk::log4cplus::FATAL_LOG_LEVEL:
+                DCMIOD_FATAL(tmpString);
+                break;
+            default:
+                DCMIOD_WARN(tmpString);
+                ;
+        }
     }
-  }
-  OFSTRINGSTREAM_FREESTR(tmpString)
-  return result;
+    OFSTRINGSTREAM_FREESTR(tmpString)
+    return result;
 }
 
-
-OFCondition DcmIODUtil::checkElementValue(const DcmElement &delem,
-                                          const OFString &vm,
-                                          const OFString &type,
-                                          const OFCondition &searchCond,
-                                          const char *moduleName,
+OFCondition DcmIODUtil::checkElementValue(const DcmElement& delem,
+                                          const OFString& vm,
+                                          const OFString& type,
+                                          const OFCondition& searchCond,
+                                          const char* moduleName,
                                           const dcmtk::log4cplus::LogLevel logLevel)
 {
-  /* call the real function */
-  return checkElementValue(&delem, delem.getTag(), vm, type, searchCond, moduleName, logLevel);
+    /* call the real function */
+    return checkElementValue(&delem, delem.getTag(), vm, type, searchCond, moduleName, logLevel);
 }
 
-
-OFCondition DcmIODUtil::getStringValueFromElement(const DcmElement &delem,
-                                                  OFString &stringValue,
-                                                  const signed long pos)
+OFCondition DcmIODUtil::getStringValueFromElement(const DcmElement& delem, OFString& stringValue, const signed long pos)
 {
-  OFCondition result = EC_Normal;
-  // cast away constness of delem; value modification can happen (eg. to remove padding)
-  if (pos < 0)
-    result = OFconst_cast(DcmElement &, delem).getOFStringArray(stringValue);
-  else
-    result = OFconst_cast(DcmElement &, delem).getOFString(stringValue, OFstatic_cast(unsigned long, pos));
-  if (result.bad())
-    stringValue.clear();
-  return result;
+    OFCondition result = EC_Normal;
+    // cast away constness of delem; value modification can happen (eg. to remove padding)
+    if (pos < 0)
+        result = OFconst_cast(DcmElement&, delem).getOFStringArray(stringValue);
+    else
+        result = OFconst_cast(DcmElement&, delem).getOFString(stringValue, OFstatic_cast(unsigned long, pos));
+    if (result.bad())
+        stringValue.clear();
+    return result;
 }
 
-
-OFCondition DcmIODUtil::getFloat64ValueFromElement(const DcmElement& delem,
-                                                   Float64& result,
-                                                   const unsigned long pos)
+OFCondition DcmIODUtil::getFloat64ValueFromElement(const DcmElement& delem, Float64& result, const unsigned long pos)
 {
-  return OFconst_cast(DcmElement &, delem).getFloat64(result, OFstatic_cast(unsigned long, pos));
+    return OFconst_cast(DcmElement&, delem).getFloat64(result, OFstatic_cast(unsigned long, pos));
 }
 
-
-OFCondition DcmIODUtil::getFloat64ValuesFromElement(const DcmElement& delem,
-                                                    OFVector<Float64>& result)
+OFCondition DcmIODUtil::getFloat64ValuesFromElement(const DcmElement& delem, OFVector<Float64>& result)
 {
-  Float64* floats = NULL;
-  OFCondition cond = OFconst_cast(DcmElement &, delem).getFloat64Array(floats);
-  if (cond.good())
-  {
-    size_t vm = OFconst_cast(DcmElement &, delem).getNumberOfValues();
-    for (size_t n = 0; n < vm; n++)
+    Float64* floats  = NULL;
+    OFCondition cond = OFconst_cast(DcmElement&, delem).getFloat64Array(floats);
+    if (cond.good())
     {
-      result.push_back(floats[n]);
+        size_t vm = OFconst_cast(DcmElement&, delem).getNumberOfValues();
+        for (size_t n = 0; n < vm; n++)
+        {
+            result.push_back(floats[n]);
+        }
     }
-  }
-  return cond;
+    return cond;
 }
 
-
-OFCondition DcmIODUtil::getStringValueFromItem(const DcmTagKey& key,
-                                               DcmItem& item,
-                                               OFString& result,
-                                               const signed long& pos)
+OFCondition
+DcmIODUtil::getStringValueFromItem(const DcmTagKey& key, DcmItem& item, OFString& result, const signed long& pos)
 {
-  DcmElement *elem = NULL;
-  item.findAndGetElement(key, elem);
-  if (elem != NULL)
-    return DcmIODUtil::getStringValueFromElement(*elem, result, pos);
-  else
-    return EC_TagNotFound;
+    DcmElement* elem = NULL;
+    item.findAndGetElement(key, elem);
+    if (elem != NULL)
+        return DcmIODUtil::getStringValueFromElement(*elem, result, pos);
+    else
+        return EC_TagNotFound;
 }
 
+OFCondition
+DcmIODUtil::getFloat64ValueFromItem(const DcmTagKey& key, DcmItem& item, Float64& result, const unsigned long& pos)
+{
+    DcmElement* elem = NULL;
+    OFCondition cond = item.findAndGetElement(key, elem);
+    if (elem != NULL)
+    {
+        cond = DcmIODUtil::getFloat64ValueFromElement(*elem, result, pos);
+    }
+    return cond;
+}
 
-OFCondition DcmIODUtil::getFloat64ValueFromItem(const DcmTagKey& key,
-                                                DcmItem& item,
-                                                Float64& result,
-                                                const unsigned long& pos)
+OFCondition DcmIODUtil::getFloat64ValuesFromItem(const DcmTagKey& key, DcmItem& item, OFVector<Float64>& result)
 {
-  DcmElement *elem = NULL;
-  OFCondition cond = item.findAndGetElement(key, elem);
-  if (elem != NULL)
-  {
-    cond = DcmIODUtil::getFloat64ValueFromElement(*elem, result, pos);
-  }
-  return cond;
+    DcmElement* elem = NULL;
+    OFCondition cond = item.findAndGetElement(key, elem);
+    if (elem != NULL)
+    {
+        cond = DcmIODUtil::getFloat64ValuesFromElement(*elem, result);
+    }
+    return cond;
 }
 
+OFCondition DcmIODUtil::setFloat64ValuesOnElement(DcmElement& delem,
+                                                  const OFVector<Float64>& values,
+                                                  const OFString& vm,
+                                                  const OFBool check)
+{
+    OFCondition result;
+    if (values.size() > OFnumeric_limits<unsigned long>::max())
+    {
+        DCMIOD_ERROR("Too many values provided (" << values.size() << " for element: " << delem.getTag().getXTag());
+        return IOD_EC_InvalidElementValue;
+    }
+    const unsigned long vmCount          = OFstatic_cast(unsigned long, values.size());
+    OFVector<Float64>::const_iterator it = values.begin();
+    for (unsigned long count = 0; count < vmCount; count++)
+    {
+        result = delem.putFloat64((*it), count);
+        if (result.bad())
+        {
+            DCMIOD_WARN(delem.getTag().getXTag() << ": Setting value "
+                                                 << " #" << count << " to \" " << *it << "\" not possible");
+        }
+        else if (check)
+        {
+            result = DcmElement::checkVM(vmCount, vm);
+        }
+        it++;
+    }
+    return result;
+}
 
-OFCondition DcmIODUtil::getFloat64ValuesFromItem(const DcmTagKey& key,
-                                                 DcmItem& item,
-                                                 OFVector<Float64>& result)
+OFCondition DcmIODUtil::getFloat32ValueFromElement(const DcmElement& delem, Float32& result, const unsigned long pos)
 {
-  DcmElement *elem = NULL;
-  OFCondition cond = item.findAndGetElement(key, elem);
-  if (elem != NULL)
-  {
-    cond = DcmIODUtil::getFloat64ValuesFromElement(*elem, result);
-  }
-  return cond;
+    return OFconst_cast(DcmElement&, delem).getFloat32(result, OFstatic_cast(unsigned long, pos));
 }
 
+OFCondition DcmIODUtil::setFloat32ValuesOnElement(DcmElement& delem,
+                                                  const OFVector<Float32>& values,
+                                                  const OFString& vm,
+                                                  const OFBool check)
+{
+    OFCondition result;
+    if (values.size() > OFnumeric_limits<unsigned long>::max())
+    {
+        DCMIOD_ERROR("Too many values provided (" << values.size() << " for element: " << delem.getTag().getXTag());
+        return IOD_EC_InvalidElementValue;
+    }
+    const unsigned long vmCount          = OFstatic_cast(unsigned long, values.size());
+    OFVector<Float32>::const_iterator it = values.begin();
+    for (unsigned long count = 0; count < vmCount; count++)
+    {
+        result = delem.putFloat32((*it), count);
+        if (result.bad())
+        {
+            DCMIOD_WARN(delem.getTag().getXTag() << ": Setting value "
+                                                 << " #" << count << " to \" " << *it << "\" not possible");
+        }
+        else if (check)
+        {
+            result = DcmElement::checkVM(vmCount, vm);
+        }
+        it++;
+    }
+    return result;
+}
 
-OFCondition DcmIODUtil::setUint16ValuesOnElement(DcmElement &delem,
+OFCondition DcmIODUtil::setUint16ValuesOnElement(DcmElementdelem,
                                                  const OFVector<Uint16>& values,
                                                  const OFString& vm,
                                                  const OFBool check)
 {
-  OFCondition result;
-  OFVector<Uint16>::const_iterator it = values.begin();
-  for (size_t count=0; count < values.size(); count++ )
-  {
-    result = delem.putUint16( (*it) );
-    if ( result.bad() )
+    OFCondition result;
+    if (values.size() > OFnumeric_limits<unsigned long>::max())
     {
-      DCMIOD_WARN(delem.getTag().getXTag() << ": Setting value " << " #" << count << " to \" " << *it << "\" not possible");
+        DCMIOD_ERROR("Too many values provided (" << values.size() << " for element: " << delem.getTag().getXTag());
+        return IOD_EC_InvalidElementValue;
     }
-    else if (check)
+    const unsigned long vmCount         = OFstatic_cast(unsigned long, values.size());
+    OFVector<Uint16>::const_iterator it = values.begin();
+    for (unsigned long count = 0; count < vmCount; count++)
     {
-      result = DcmElement::checkVM(OFstatic_cast(unsigned long, values.size()), vm);
+        result = delem.putUint16((*it), count);
+        if (result.bad())
+        {
+            DCMIOD_WARN(delem.getTag().getXTag() << ": Setting value "
+                                                 << " #" << count << " to \" " << *it << "\" not possible");
+        }
+        else if (check)
+        {
+            result = DcmElement::checkVM(vmCount, vm);
+        }
+        it++;
     }
-    it++;
-  }
-  return result;
+    return result;
 }
 
-
-OFCondition DcmIODUtil::getUint16ValuesFromElement(DcmElement &delem,
-                                                   OFVector<Uint16>& values)
+OFCondition DcmIODUtil::getUint16ValuesFromElement(DcmElement& delem, OFVector<Uint16>& values)
 {
-  OFCondition result;
-  const size_t count = delem.getNumberOfValues();
-  values.reserve(count);
-  for (size_t i = 0;  i < count; i++)
-  {
-    Uint16 val;
-    result = delem.getUint16(val, OFstatic_cast(unsigned long, i));
-    if (result.bad())
+    OFCondition result;
+    const size_t count = delem.getNumberOfValues();
+    values.reserve(count);
+    for (size_t i = 0; i < count; i++)
     {
-      DCMIOD_WARN(delem.getTag().getXTag() << ": Getting value " << " #" << i << " not possible");
-      break;
+        Uint16 val;
+        result = delem.getUint16(val, OFstatic_cast(unsigned long, i));
+        if (result.bad())
+        {
+            DCMIOD_WARN(delem.getTag().getXTag() << ": Getting value "
+                                                 << " #" << i << " not possible");
+            break;
+        }
+        values.push_back(val);
     }
-    values.push_back(val);
-  }
-  return result;
+    return result;
 }
 
-
 void DcmIODUtil::checkSubSequence(OFCondition& result,
                                   DcmItem& surroundingItem,
                                   const DcmTagKey& seqKey,
@@ -466,152 +537,230 @@ void DcmIODUtil::checkSubSequence(OFCondition& result,
                                   const OFString& module,
                                   const dcmtk::log4cplus::LogLevel logLevel)
 {
-  OFCondition exists = EC_Normal;
-  /* check result */
-  if ( result.good() )
-  {
-    DcmSequenceOfItems *seq = NULL;
-    exists = surroundingItem.findAndGetSequence(seqKey, seq);
-    result = DcmIODUtil::checkElementValue(seq, seqKey, cardinality, type, exists, module.c_str(), logLevel);
-  }
-}
-
-
-OFCondition DcmIODUtil::getAndCheckSingleItem(DcmSequenceOfItems& seq,
-                                              DcmItem*& item,
-                                              const DcmTagKey& checkKey)
-{
-  item = NULL;
-  const OFString tagName = OFconst_cast(DcmTag*, &seq.getTag())->getTagName(); // getTagName is not const...
-  if (checkKey != DCM_UndefinedTagKey)
-  {
-    if (seq.getTag().getXTag() != checkKey)
-    {
-      DCMIOD_ERROR("Expected sequence " << checkKey << " but got " << &seq.getTag() << "(" << tagName << ")");
-      return EC_ItemNotFound;
-    }
-  }
-
-  // get actual tag name and cardinality
-  const unsigned long card = seq.card();
-  if (card != 1)
-  {
-    if (card > 1)
-    {
-      DCMIOD_WARN("Only single item allowed in " << tagName << ", ignoring " << card -1 << " other items");
-    }
-    else // card = 0
-    {
-      DCMIOD_WARN("Cannot read from sequence " << tagName << ": No item found");
-      return EC_ItemNotFound;
-    }
-  }
-  // get item and return it
-  item = seq.getItem(0);
-  if (item == NULL)
-  {
-    DCMIOD_ERROR("Cannot read item from " << tagName << ": No item found (internal error)");
-    return EC_CorruptedData;
-  }
-  return EC_Normal;
-}
-
-
-OFCondition DcmIODUtil::checkSOPClass(DcmItem* item,
-                                      const OFString& desiredSOPClass,
-                                      OFString& valueFound)
-{
-  valueFound.clear();
-  if ( (item == NULL) || (item->card() == 0) )
-  {
-    DCMIOD_TRACE("Cannot check SOP Class UID: Dataset not present or empty");
-    return EC_IllegalParameter;
-  }
-  OFCondition result = item->findAndGetOFString(DCM_SOPClassUID, valueFound);
-  if ( result.bad() )
-  {
-    DCMIOD_TRACE("No SOP Class UID in file, giving up");
-    return EC_TagNotFound;
-  }
-  if (valueFound != desiredSOPClass)
-  {
-    DCMIOD_TRACE("File is not of SOP Class " << desiredSOPClass << ", but instead SOP Class is " << dcmFindNameOfUID(valueFound.c_str(), valueFound.c_str()) );
-    return EC_InvalidValue;
-  }
-  return EC_Normal;
-}
-
-
-OFBool DcmIODUtil::isSequenceTag(const DcmTagKey& key,
-                                 const OFString& privateCreator)
-{
-  const DcmDataDictionary& globalDataDict = dcmDataDict.rdlock();
-  const DcmDictEntry *dictRef = NULL;
-  if (privateCreator.empty())
-    dictRef = globalDataDict.findEntry(key, NULL);
-  else
-    dictRef = globalDataDict.findEntry(key, privateCreator.c_str());
-  DcmVR vr;
-  if (dictRef)
-  {
-    vr = dictRef->getVR();
-  }
-  dcmDataDict.rdunlock();
-  if (vr.getEVR() == EVR_SQ)
-    return OFTrue;
-  return OFFalse;
+    OFCondition exists = EC_Normal;
+    /* check result */
+    if (result.good())
+    {
+        DcmSequenceOfItems* seq = NULL;
+        exists                  = surroundingItem.findAndGetSequence(seqKey, seq);
+        result = DcmIODUtil::checkElementValue(seq, seqKey, cardinality, type, exists, module.c_str(), logLevel);
+    }
 }
 
+OFCondition DcmIODUtil::getAndCheckSingleItem(DcmSequenceOfItems& seq, DcmItem*& item, const DcmTagKey& checkKey)
+{
+    item                   = NULL;
+    const OFString tagName = OFconst_cast(DcmTag*, &seq.getTag())->getTagName(); // getTagName is not const...
+    if (checkKey != DCM_UndefinedTagKey)
+    {
+        if (seq.getTag().getXTag() != checkKey)
+        {
+            DCMIOD_ERROR("Expected sequence " << checkKey << " but got " << &seq.getTag() << "(" << tagName << ")");
+            return EC_ItemNotFound;
+        }
+    }
 
-const DcmTagKey DcmIODUtil::parseTagKey(const OFString& keyString)
+    // get actual tag name and cardinality
+    const unsigned long card = seq.card();
+    if (card != 1)
+    {
+        if (card > 1)
+        {
+            DCMIOD_WARN("Only single item allowed in " << tagName << ", ignoring " << card - 1 << " other items");
+        }
+        else // card = 0
+        {
+            DCMIOD_WARN("Cannot read from sequence " << tagName << ": No item found");
+            return EC_ItemNotFound;
+        }
+    }
+    // get item and return it
+    item = seq.getItem(0);
+    if (item == NULL)
+    {
+        DCMIOD_ERROR("Cannot read item from " << tagName << ": No item found (internal error)");
+        return EC_CorruptedData;
+    }
+    return EC_Normal;
+}
+
+OFCondition DcmIODUtil::checkSOPClass(DcmItem* item, const OFString& desiredSOPClass, OFString& valueFound)
 {
-  unsigned int g, e;
-  DcmTagKey resultKey = DCM_UndefinedTagKey;
-  if (sscanf(keyString.c_str(), "(%x,%x)", &g, &e) == 2)
-  {
-    resultKey.set(OFstatic_cast(Uint16, g), OFstatic_cast(Uint16, e));
-  }
-  return resultKey;
+    valueFound.clear();
+    if ((item == NULL) || (item->card() == 0))
+    {
+        DCMIOD_TRACE("Cannot check SOP Class UID: Dataset not present or empty");
+        return EC_IllegalParameter;
+    }
+    OFCondition result = item->findAndGetOFString(DCM_SOPClassUID, valueFound);
+    if (result.bad())
+    {
+        DCMIOD_TRACE("No SOP Class UID in file, giving up");
+        return EC_TagNotFound;
+    }
+    if (valueFound != desiredSOPClass)
+    {
+        DCMIOD_TRACE("File is not of SOP Class " << desiredSOPClass << ", but instead SOP Class is "
+                                                 << dcmFindNameOfUID(valueFound.c_str(), valueFound.c_str()));
+        return EC_InvalidValue;
+    }
+    return EC_Normal;
 }
 
+OFBool DcmIODUtil::isSequenceTag(const DcmTagKey& key, const OFString& privateCreator)
+{
+    const DcmDataDictionary& globalDataDict = dcmDataDict.rdlock();
+    const DcmDictEntry* dictRef             = NULL;
+    if (privateCreator.empty())
+        dictRef = globalDataDict.findEntry(key, NULL);
+    else
+        dictRef = globalDataDict.findEntry(key, privateCreator.c_str());
+    DcmVR vr;
+    if (dictRef)
+    {
+        vr = dictRef->getVR();
+    }
+    dcmDataDict.rdunlock();
+    if (vr.getEVR() == EVR_SQ)
+        return OFTrue;
+    return OFFalse;
+}
+
+const DcmTagKey DcmIODUtil::parseTagKey(const OFString& keyString)
+{
+    unsigned int g, e;
+    DcmTagKey resultKey = DCM_UndefinedTagKey;
+    if (sscanf(keyString.c_str(), "(%x,%x)", &g, &e) == 2)
+    {
+        resultKey.set(OFstatic_cast(Uint16, g), OFstatic_cast(Uint16, e));
+    }
+    return resultKey;
+}
 
 OFCondition DcmIODUtil::decompress(DcmDataset& dset)
 {
-  DcmXfer xfer = dset.getOriginalXfer();
-  if (xfer.isEncapsulated())
-  {
-    if (EC_Normal != dset.chooseRepresentation(EXS_LittleEndianExplicit, NULL))
+    DcmXfer xfer = dset.getOriginalXfer();
+    if (xfer.isEncapsulated())
     {
-      DCMIOD_ERROR("No conversion to uncompressed transfer syntax possible!");
-      return IOD_EC_CannotDecompress;
+        if (EC_Normal != dset.chooseRepresentation(EXS_LittleEndianExplicit, NULL))
+        {
+
+            DCMIOD_ERROR("No conversion from " << xfer.getXferName() << " to uncompressed transfer syntax possible!");
+            return IOD_EC_CannotDecompress;
+        }
     }
-  }
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 OFString DcmIODUtil::createUID(const Uint8 level)
 {
-  char uid[100];
-  switch (level)
-  {
-    case 0: dcmGenerateUniqueIdentifier(uid, SITE_INSTANCE_UID_ROOT); break;
-    case 1: dcmGenerateUniqueIdentifier(uid, SITE_SERIES_UID_ROOT); break;
-    case 2: dcmGenerateUniqueIdentifier(uid, SITE_STUDY_UID_ROOT); break;
-    default: dcmGenerateUniqueIdentifier(uid, SITE_STUDY_UID_ROOT);
-  }
-  return uid;
+    char uid[100];
+    switch (level)
+    {
+        case 0:
+            dcmGenerateUniqueIdentifier(uid, SITE_INSTANCE_UID_ROOT);
+            break;
+        case 1:
+            dcmGenerateUniqueIdentifier(uid, SITE_SERIES_UID_ROOT);
+            break;
+        case 2:
+            dcmGenerateUniqueIdentifier(uid, SITE_STUDY_UID_ROOT);
+            break;
+        default:
+            dcmGenerateUniqueIdentifier(uid, SITE_STUDY_UID_ROOT);
+    }
+    return uid;
+}
+
+Uint32 DcmIODUtil::limitMaxFrames(const size_t numFramesPresent, const OFString& warning)
+{
+    if (numFramesPresent > 2147483647)
+    {
+        DCMIOD_WARN(warning);
+        return 2147483647;
+    }
+    return OFstatic_cast(Uint16, numFramesPresent);
 }
 
+OFCondition DcmIODUtil::extractBinaryFrames(Uint8* pixData,
+                                            const size_t numFrames,
+                                            const size_t bitsPerFrame,
+                                            OFVector<DcmIODTypes::Frame*>& results)
+{
+    // Will hold the bit position (0-7) that the current frame starts from. The
+    // first frame will always start at bit 0.
+    Uint8 bitShift = 0;
+    // Compute length in bytes we need to consider for each frame.
+    size_t frameLengthBytes = bitsPerFrame / 8;
+    // If the number of bits is not dividable by 8, we need part of an extra
+    // byte in the end. Since we like to set the unused bits to 0 in such a last
+    // byte to 0, remember the number.
+    size_t overlapBits = (8 - (bitsPerFrame % 8)) % 8;
+    // Add an extra byte if we we fill a partial byte in the end
+    if (overlapBits != 0)
+        frameLengthBytes++;
+    // Points to current reading position within pixData
+    Uint8* readPos = pixData;
+    // Loop over each frame and copy it to Frame structures
+    for (size_t f = 0; f < numFrames; f++)
+    {
+        // Create frame with correct length and copy 1:1 from pixel data
+        DcmIODTypes::Frame* frame = new DcmIODTypes::Frame();
+        frame->length             = frameLengthBytes;
+        frame->pixData            = new Uint8[frameLengthBytes];
+        if (!frame->pixData)
+        {
+            delete frame;
+            return EC_MemoryExhausted;
+        }
+        memcpy(frame->pixData, readPos, frame->length);
+        // If we have been copying too much, i.e the first bits of the frame
+        // actually belong to the former frame, shift the whole frame this amount
+        // of bits to the left in order to shift the superfluous bits out, i.e.
+        // make frame start at byte boundary.
+        if (bitShift > 0)
+        {
+            DcmIODUtil::alignFrameOnByteBoundary(frame->pixData, frame->length, 8 - bitShift);
+        }
+        // Adapt last byte by masking out unused bits (i.e. those belonging to next frame).
+        // A reader should ignore those unused bits anyway.
+        frame->pixData[frame->length - 1] = (frame->pixData[frame->length - 1] << (overlapBits)) >> (overlapBits);
+        // Store frame
+        results.push_back(frame);
+        // Compute the bitshift created by this frame
+        bitShift = (8 - ((f + 1) * bitsPerFrame) % 8) % 8;
+        // If the previous byte read has not been used completely, i.e. it contains
+        // also bytes of the next frame, rewind read position to the previous byte
+        // that was partially read. Otherwise skip to the next full byte.
+        if (bitShift > 0)
+        {
+            readPos = readPos + frame->length - 1;
+        }
+        else
+        {
+            readPos = readPos + frame->length;
+        }
+    }
+    return EC_Normal;
+}
 
-Uint32 DcmIODUtil::limitMaxFrames(const size_t numFramesPresent,
-                                  const OFString& warning)
+void DcmIODUtil::alignFrameOnByteBoundary(Uint8* buf, size_t bufLen, Uint8 numBits)
 {
-  if (numFramesPresent > 2147483647)
-  {
-    DCMIOD_WARN(warning);
-    return 2147483647;
-  }
-  return OFstatic_cast(Uint16, numFramesPresent);
+    if (numBits > 7)
+    {
+        DCMIOD_ERROR("Invalid input data: alignFrameOnByteBoundary() can only shift 0-7 bits");
+        return;
+    }
+    for (size_t x = 0; x < bufLen - 1; x++)
+    {
+        // Shift current byte
+        buf[x] = buf[x] >> numBits;
+        // isolate portion of next byte that must be shifted into current byte
+        Uint8 next = (buf[x + 1] << (8 - numBits));
+        // Take over portion from next byte
+        buf[x] |= next;
+    }
+    // Shift last byte manually
+    buf[bufLen - 1] >>= numBits;
 }
index ceedbb2f2f85c9f81ff67f06f1305abc4cd6bad0..0796b9006bfdfaccc6effc626f2bda5ecaa662d1 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modacquisitioncontext.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/iodutil.h"
 
 const OFString IODAcquisitionContextModule::m_ModuleName = "AcquisitionContextModule";
 
-
-IODAcquisitionContextModule::IODAcquisitionContextModule(OFshared_ptr<DcmItem> item,
-                                                         OFshared_ptr<IODRules> rules)
-: IODModule(item, rules)
+IODAcquisitionContextModule::IODAcquisitionContextModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODModule(item, rules)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODAcquisitionContextModule::IODAcquisitionContextModule()
-: IODModule()
+    : IODModule()
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 OFString IODAcquisitionContextModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 void IODAcquisitionContextModule::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_AcquisitionContextSequence, "1-n","2", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_AcquisitionContextSequence, "1-n", "2", getName(), DcmIODTypes::IE_INSTANCE),
+                     OFTrue);
 }
 
-
 IODAcquisitionContextModule::~IODAcquisitionContextModule()
 {
 }
 
-
 // --- get attributes (C++ string) ---
 
 // --- set attributes ---
index 9ecde195208868664db8a2ff365e67a7ca4c474a..03528bca15a9e84594f2a385a7235c6ee06f0149 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2017, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modbase.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+#include "dcmtk/dcmdata/dcdeftag.h"
 #include "dcmtk/dcmdata/dcitem.h"
-#include "dcmtk/dcmiod/iodutil.h"
 #include "dcmtk/dcmiod/iodrules.h"
-#include "dcmtk/dcmdata/dcdeftag.h"
-
+#include "dcmtk/dcmiod/iodutil.h"
 
 IODComponent::IODComponent(const IODComponent& rhs)
-: m_Item(OFstatic_cast(DcmItem*, rhs.m_Item->clone()))
-, m_Rules(rhs.m_Rules->clone())
-, m_Parent(OFnullptr)
+    : m_Item(OFstatic_cast(DcmItem*, rhs.m_Item->clone()))
+    , m_Rules(rhs.m_Rules->clone())
+    , m_Parent(OFnullptr)
 {
-
 }
 
-
-IODComponent::IODComponent(OFshared_ptr<DcmItem> item,
-                           OFshared_ptr<IODRules> rules,
-                           IODComponent* parent)
-: m_Item(item),
-  m_Rules(rules),
-  m_Parent(parent)
+IODComponent::IODComponent(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules, IODComponent* parent)
+    : m_Item(item)
+    , m_Rules(rules)
+    , m_Parent(parent)
 {
-  if (!m_Item)
-    m_Item.reset(new DcmItem());
+    if (!m_Item)
+        m_Item.reset(new DcmItem());
 
-  if (!m_Rules)
-    m_Rules.reset(new IODRules());
+    if (!m_Rules)
+        m_Rules.reset(new IODRules());
 }
 
-
 IODComponent::IODComponent(IODComponent* parent)
-: m_Item(),
-  m_Rules(),
-  m_Parent(parent)
+    : m_Item()
+    , m_Rules()
+    , m_Parent(parent)
 {
-  m_Item.reset(new DcmItem());
-  m_Rules.reset(new IODRules());
+    m_Item.reset(new DcmItem());
+    m_Rules.reset(new IODRules());
 }
 
-
 IODComponent::~IODComponent()
 {
-  // Nothing to do for shared pointers
+    // Nothing to do for shared pointers
 }
 
-
 IODComponent& IODComponent::operator=(const IODComponent& rhs)
 {
-  if (&rhs != this)
-  {
-    m_Item.reset(OFstatic_cast(DcmItem*, rhs.m_Item->clone()));
-    m_Rules.reset(rhs.m_Rules->clone());
-    m_Parent = OFnullptr;
-  }
-  return *this;
+    if (&rhs != this)
+    {
+        m_Item.reset(OFstatic_cast(DcmItem*, rhs.m_Item->clone()));
+        m_Rules.reset(rhs.m_Rules->clone());
+        m_Parent = OFnullptr;
+    }
+    return *this;
 }
 
-
 void IODComponent::inventMissing()
 {
-  // Try to fill in missing type 1 information
-  OFVector<IODRule*> writeRules = m_Rules->getByModule(getName());
-  OFVector<IODRule*>::iterator rule = writeRules.begin();
-  while (rule != writeRules.end())
-  {
-    OFString val = (*rule)->getDefaultValue() ;
-    // We have a default value
-    if ( val.length() != 0 )
+    // Try to fill in missing type 1 information
+    OFVector<IODRule*> writeRules     = m_Rules->getByModule(getName());
+    OFVector<IODRule*>::iterator rule = writeRules.begin();
+    while (rule != writeRules.end())
     {
-      // Check if element is not set
-      DcmElement *elem = NULL;
-      if ( getData().findAndGetElement( (*rule)->getTagKey(), elem ).bad() )
-      {
-        elem = DcmItem::newDicomElement((*rule)->getTagKey());
-        if (elem == NULL)
-        {
-          DCMIOD_ERROR("Could not allocate element " << (*rule)->getTagKey());
-        }
-        else
+        OFString val = (*rule)->getDefaultValue();
+        // We have a default value
+        if (val.length() != 0)
         {
-          elem->putString(val.c_str());
-          m_Item->insert(elem);
+            // Check if element is not set
+            DcmElement* elem = NULL;
+            if (getData().findAndGetElement((*rule)->getTagKey(), elem).bad())
+            {
+                elem = DcmItem::newDicomElement((*rule)->getTagKey());
+                if (elem == NULL)
+                {
+                    DCMIOD_ERROR("Could not allocate element " << (*rule)->getTagKey());
+                }
+                else
+                {
+                    elem->putString(val.c_str());
+                    m_Item->insert(elem);
+                }
+            }
+            else if (elem->getLength() == 0)
+            {
+                elem->putString(val.c_str());
+            }
         }
-      }
-      else if (elem->getLength() == 0)
-      {
-        elem->putString(val.c_str());
-      }
+        rule++;
     }
-    rule++;
-  }
 }
 
-
 void IODComponent::clearData()
 {
-  OFVector<IODRule*> modRules = m_Rules->getByModule(getName());
-  OFVector<IODRule*>::iterator rule = modRules.begin();
-  while (rule != modRules.end())
-  {
-    m_Item->findAndDeleteElement( (*rule)->getTagKey() );
-    rule++;
-  }
+    OFVector<IODRule*> modRules       = m_Rules->getByModule(getName());
+    OFVector<IODRule*>::iterator rule = modRules.begin();
+    while (rule != modRules.end())
+    {
+        m_Item->findAndDeleteElement((*rule)->getTagKey());
+        rule++;
+    }
 }
 
-
 void IODComponent::makeOptional()
 {
-  OFVector<IODRule*> modRules = m_Rules->getByModule(getName());
-  OFVector<IODRule*>::iterator rule = modRules.begin();
-  while (rule != modRules.end())
-  {
-    (*rule)->setType("3");
-    rule++;
-  }
+    OFVector<IODRule*> modRules       = m_Rules->getByModule(getName());
+    OFVector<IODRule*>::iterator rule = modRules.begin();
+    while (rule != modRules.end())
+    {
+        (*rule)->setType("3");
+        rule++;
+    }
 }
 
-
-OFCondition IODComponent::read(DcmItem& source,
-                               const OFBool clearOldData)
+OFCondition IODComponent::read(DcmItem& source, const OFBool clearOldData)
 {
-  // Debug
-  DCMIOD_DEBUG("Reading component: " << getName());
+    // Debug
+    DCMIOD_DEBUG("Reading component: " << getName());
 
-  // Clear old data if desired
-  if (clearOldData)
-  {
-    clearData();
-  }
+    // Clear old data if desired
+    if (clearOldData)
+    {
+        clearData();
+    }
 
-  // Do actual reading
-  read(source, *m_Rules, *m_Item, getName());
-  // We do not report errors here (only logger output)
-  return EC_Normal;
+    // Do actual reading
+    read(source, *m_Rules, *m_Item, getName());
+    // We do not report errors here (only logger output)
+    return EC_Normal;
 }
 
-
 OFCondition IODComponent::write(DcmItem& destination)
 {
-  // Debug
-  DCMIOD_DEBUG("Writing component: " << getName());
+    // Debug
+    DCMIOD_DEBUG("Writing component: " << getName());
 
-  // Invent missing values
-  inventMissing();
+    // Invent missing values
+    inventMissing();
 
-  // Start writing
-  OFCondition result = EC_Normal;
-  result = write(*m_Item, *m_Rules, destination, getName());
-  return result;
+    // Start writing
+    OFCondition result = EC_Normal;
+    result             = write(*m_Item, *m_Rules, destination, getName());
+    return result;
 }
 
-
 int IODComponent::compare(const IODComponent& rhs) const
 {
-  return this->m_Item.get()->compare( *(rhs.m_Item.get()) ) ;
+    return this->m_Item.get()->compare(*(rhs.m_Item.get()));
 }
 
-
 OFCondition IODComponent::check(const OFBool quiet)
 {
-  OFCondition result;
-  IODRules::iterator it = m_Rules->begin();
-  while (it != m_Rules->end())
-  {
-    result = (*it).second->check(*m_Item, quiet);
-    if (result.bad())
-      break;
-    else
-      it++;
-  }
-  return result;
+    OFCondition result;
+    IODRules::iterator it = m_Rules->begin();
+    while (it != m_Rules->end())
+    {
+        result = (*it).second->check(*m_Item, quiet);
+        if (result.bad())
+            break;
+        else
+            it++;
+    }
+    return result;
 }
 
-
 // static helper
-OFCondition IODComponent::read(DcmItem& source,
-                               IODRules& rules,
-                               DcmItem& destination,
-                               const OFString& componentName)
+OFCondition IODComponent::read(DcmItem& source, IODRules& rules, DcmItem& destination, const OFString& componentName)
 {
-  OFVector<IODRule*> modRules = rules.getByModule(componentName);
-  OFVector<IODRule*>::iterator rule = modRules.begin();
-  while (rule != modRules.end())
-  {
-    // We do not read/copy sequences but only check them since they are not
-    // handled within this component
-    OFBool isSequence = ( DcmTag( (*rule)->getTagKey()).getEVR() == EVR_SQ);
-    if (isSequence)
-    {
-      DcmElement *elem = NULL;
-      OFCondition cond = source.findAndGetElement( (*rule)->getTagKey(), elem);
-      DcmIODUtil::checkElementValue(elem, (*rule)->getTagKey(), (*rule)->getVM(), (*rule)->getType(), cond, (*rule)->getModule().c_str(), dcmtk::log4cplus::WARN_LOG_LEVEL);
-    }
-    else // Normal attributes are checked and copied over into this IOD component
+    OFVector<IODRule*> modRules       = rules.getByModule(componentName);
+    OFVector<IODRule*>::iterator rule = modRules.begin();
+    while (rule != modRules.end())
     {
-      DcmElement* elem = NULL;
-      DcmIODUtil::getAndCheckElementFromDataset(source, elem, *rule);
-      if (elem != NULL)
-      {
-        OFCondition result = destination.insert(elem, OFTrue);
-        if (result.bad())
+        // We do not read/copy sequences but only check them since they are not
+        // handled within this component
+        OFBool isSequence = (DcmTag((*rule)->getTagKey()).getEVR() == EVR_SQ);
+        if (isSequence)
+        {
+            DcmElement* elem = NULL;
+            OFCondition cond = source.findAndGetElement((*rule)->getTagKey(), elem);
+            DcmIODUtil::checkElementValue(elem,
+                                          (*rule)->getTagKey(),
+                                          (*rule)->getVM(),
+                                          (*rule)->getType(),
+                                          cond,
+                                          (*rule)->getModule().c_str(),
+                                          dcmtk::log4cplus::WARN_LOG_LEVEL);
+        }
+        else // Normal attributes are checked and copied over into this IOD component
         {
-          DCMIOD_ERROR("Cannot insert element with tag: " << (*rule)->getTagKey());
-          delete elem;
+            DcmElement* elem = NULL;
+            DcmIODUtil::getAndCheckElementFromDataset(source, elem, *rule);
+            if (elem != NULL)
+            {
+                OFCondition result = destination.insert(elem, OFTrue);
+                if (result.bad())
+                {
+                    DCMIOD_ERROR("Cannot insert element with tag: " << (*rule)->getTagKey());
+                    delete elem;
+                }
+            }
         }
-      }
+        rule++;
     }
-    rule++;
-  }
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 // static helper
-OFCondition IODComponent::write(DcmItem& source,
-                                IODRules& rules,
-                                DcmItem& destination,
-                                const OFString& componentName)
+OFCondition IODComponent::write(DcmItem& source, IODRules& rules, DcmItem& destination, const OFString& componentName)
 {
-  OFCondition result = EC_Normal;
+    OFCondition result = EC_Normal;
 
-  OFVector<IODRule*> writeRules = rules.getByModule(componentName);
-  OFVector<IODRule*>::iterator rule = writeRules.begin();
-  while (rule != writeRules.end())
-  {
-    DcmElement* elem = NULL;
-    source.findAndGetElement( (*rule)->getTagKey(), elem, OFFalse /* only this level */, OFTrue /* create copy*/);
-    DcmIODUtil::addElementToDataset(result, destination, elem, *rule);
-    rule++;
-  }
+    OFVector<IODRule*> writeRules     = rules.getByModule(componentName);
+    OFVector<IODRule*>::iterator rule = writeRules.begin();
+    while (rule != writeRules.end())
+    {
+        DcmElement* elem = NULL;
+        source.findAndGetElement((*rule)->getTagKey(), elem, OFFalse /* only this level */, OFTrue /* create copy*/);
+        DcmIODUtil::addElementToDataset(result, destination, elem, *rule);
+        rule++;
+    }
 
-  return result;
+    return result;
 }
 
-
 // -------- IODModule --------------
 
-IODModule::IODModule(): IODComponent()
+IODModule::IODModule()
+    : IODComponent()
 {
-  // nothing to do, IODComponent does the work
+    // nothing to do, IODComponent does the work
 }
 
-
 IODModule::IODModule(const IODModule& rhs)
-: IODComponent(rhs.m_Item, rhs.m_Rules, rhs.m_Parent)
+    : IODComponent(rhs.m_Item, rhs.m_Rules, rhs.m_Parent)
 {
-
 }
 
-
-IODModule::IODModule(OFshared_ptr< DcmItem > item,
-  OFshared_ptr< IODRules > rules)
-: IODComponent(item, rules, NULL /* No parent for modules */)
+IODModule::IODModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODComponent(item, rules, NULL /* No parent for modules */)
 {
-  // nothing to do, IODComponent does the work
+    // nothing to do, IODComponent does the work
 }
 
-
 IODModule& IODModule::operator=(const IODModule& rhs)
 {
-  if (this != &rhs)
-  {
-    m_Item = rhs.m_Item;
-    m_Rules = rhs.m_Rules;
-    m_Parent = rhs.m_Parent;
-  }
-  return *this;
+    if (this != &rhs)
+    {
+        m_Item   = rhs.m_Item;
+        m_Rules  = rhs.m_Rules;
+        m_Parent = rhs.m_Parent;
+    }
+    return *this;
 }
index baeba89857b8f3c6c2ecca8f8784364b01a2b8b1..69fa960250e910595dbbfda090db964d87f75618 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"
 #include "dcmtk/dcmiod/modcommoninstanceref.h"
+#include "dcmtk/config/osconfig.h"
 #include "dcmtk/dcmiod/iodutil.h" // for static helpers
 
 const OFString IODCommonInstanceReferenceModule::m_ComponentName = "CommonInstanceReferenceModule";
-const OFString IODCommonInstanceReferenceModule::StudiesOtherInstancesItem::m_ComponentName = "StudiesContainingOtherReferencedInstancesSequence";
-
-
-IODCommonInstanceReferenceModule::IODCommonInstanceReferenceModule(OFshared_ptr< DcmItem > item,
-                                                                   OFshared_ptr< IODRules > rules)
-: IODModule(item, rules),
-  m_ReferenceSeriesItems(),
-  m_StudiesContainingOtherReferencedInstancesSequence()
+const OFString IODCommonInstanceReferenceModule::StudiesOtherInstancesItem::m_ComponentName
+    = "StudiesContainingOtherReferencedInstancesSequence";
+
+IODCommonInstanceReferenceModule::IODCommonInstanceReferenceModule(OFshared_ptr<DcmItem> item,
+                                                                   OFshared_ptr<IODRules> rules)
+    : IODModule(item, rules)
+    , m_ReferenceSeriesItems()
+    , m_StudiesContainingOtherReferencedInstancesSequence()
 {
-  resetRules();
+    resetRules();
 }
 
-
 IODCommonInstanceReferenceModule::IODCommonInstanceReferenceModule()
-: IODModule(),
-  m_ReferenceSeriesItems(),
-  m_StudiesContainingOtherReferencedInstancesSequence()
+    : IODModule()
+    , m_ReferenceSeriesItems()
+    , m_StudiesContainingOtherReferencedInstancesSequence()
 {
-  resetRules();
+    resetRules();
 }
 
-
 IODCommonInstanceReferenceModule::~IODCommonInstanceReferenceModule()
 {
-  freeMemory();
+    freeMemory();
 }
 
-
 OFString IODCommonInstanceReferenceModule::getName() const
 {
-  return m_ComponentName;
+    return m_ComponentName;
 }
 
-
-OFVector< IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem* >& IODCommonInstanceReferenceModule::getReferencedSeriesItems()
+OFVector<IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem*>&
+IODCommonInstanceReferenceModule::getReferencedSeriesItems()
 {
-  return m_ReferenceSeriesItems;
+    return m_ReferenceSeriesItems;
 }
 
-
-OFVector<IODCommonInstanceReferenceModule::StudiesOtherInstancesItem *> & IODCommonInstanceReferenceModule::getStudiesContainingOtherReferences()
+OFVector<IODCommonInstanceReferenceModule::StudiesOtherInstancesItem*>&
+IODCommonInstanceReferenceModule::getStudiesContainingOtherReferences()
 {
-  return m_StudiesContainingOtherReferencedInstancesSequence;
+    return m_StudiesContainingOtherReferencedInstancesSequence;
 }
 
-
 void IODCommonInstanceReferenceModule::clearData()
 {
-  freeMemory();
+    freeMemory();
 }
 
-
-OFCondition IODCommonInstanceReferenceModule::read(DcmItem& source,
-                                                   const OFBool clearOldData)
+OFCondition IODCommonInstanceReferenceModule::read(DcmItem& source, const OFBool clearOldData)
 {
-  if (clearOldData)
-    clearData();
+    if (clearOldData)
+        clearData();
 
-  DcmIODUtil::readSubSequence(source, DCM_ReferencedSeriesSequence, m_ReferenceSeriesItems, m_Rules->getByTag(DCM_ReferencedSeriesSequence));
-  DcmIODUtil::readSubSequence(source,
-                              DCM_StudiesContainingOtherReferencedInstancesSequence,
-                              m_StudiesContainingOtherReferencedInstancesSequence,
-                              m_Rules->getByTag(DCM_StudiesContainingOtherReferencedInstancesSequence));
+    DcmIODUtil::readSubSequence(
+        source, DCM_ReferencedSeriesSequence, m_ReferenceSeriesItems, m_Rules->getByTag(DCM_ReferencedSeriesSequence));
+    DcmIODUtil::readSubSequence(source,
+                                DCM_StudiesContainingOtherReferencedInstancesSequence,
+                                m_StudiesContainingOtherReferencedInstancesSequence,
+                                m_Rules->getByTag(DCM_StudiesContainingOtherReferencedInstancesSequence));
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 OFCondition IODCommonInstanceReferenceModule::write(DcmItem& destination)
 {
-  OFCondition result = EC_Normal;
-
-  DcmIODUtil::writeSubSequence<OFVector<IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem*> >(result, DCM_ReferencedSeriesSequence, m_ReferenceSeriesItems, *m_Item, m_Rules->getByTag(DCM_ReferencedSeriesSequence));
-  DcmIODUtil::writeSubSequence<OFVector<StudiesOtherInstancesItem*> >(result,
-                                                                      DCM_StudiesContainingOtherReferencedInstancesSequence,
-                                                                      m_StudiesContainingOtherReferencedInstancesSequence,
-                                                                      *m_Item,
-                                                                      m_Rules->getByTag(DCM_StudiesContainingOtherReferencedInstancesSequence));
-  if (result.good()) result = IODModule::write(destination);
-  return result;
+    OFCondition result = EC_Normal;
+
+    DcmIODUtil::writeSubSequence<OFVector<IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem*> >(
+        result,
+        DCM_ReferencedSeriesSequence,
+        m_ReferenceSeriesItems,
+        *m_Item,
+        m_Rules->getByTag(DCM_ReferencedSeriesSequence));
+    DcmIODUtil::writeSubSequence<OFVector<StudiesOtherInstancesItem*> >(
+        result,
+        DCM_StudiesContainingOtherReferencedInstancesSequence,
+        m_StudiesContainingOtherReferencedInstancesSequence,
+        *m_Item,
+        m_Rules->getByTag(DCM_StudiesContainingOtherReferencedInstancesSequence));
+    if (result.good())
+        result = IODModule::write(destination);
+    return result;
 }
 
-
-size_t IODCommonInstanceReferenceModule::addReferences(
-  const IODReferences& references,
-  const OFString& studyInstanceUID,
-  const OFBool clearOldData)
+size_t IODCommonInstanceReferenceModule::addReferences(const IODReferences& references,
+                                                       const OFString& studyInstanceUID,
+                                                       const OFBool clearOldData)
 {
-  if (clearOldData)
-  {
-    clearData();
-  }
-  OFString ourStudy = studyInstanceUID;
-  if (ourStudy.empty())
-  {
-    m_Item->findAndGetOFString(DCM_StudyInstanceUID, ourStudy);
-    if (ourStudy.empty())
+    if (clearOldData)
     {
-      DCMIOD_ERROR("Could not add references: No Study Instance UID specified for \"this\" object");
-      return 0;
+        clearData();
     }
-  }
-
-  const OFVector<IODReference*> refs = references.get();
-  OFVector<IODReference*>::const_iterator ref = refs.begin();
-  size_t count = 0;
-  while (ref != refs.end())
-  {
-    OFCondition result;
-    // If reference belongs into "this" study, add it to Referenced Series Sequence
-    OFString refStudy = (*ref)->m_StudyInstanceUID;
-    if ( refStudy == ourStudy )
+    OFString ourStudy = studyInstanceUID;
+    if (ourStudy.empty())
     {
-     result = addSeriesReference(m_ReferenceSeriesItems, **ref);
+        m_Item->findAndGetOFString(DCM_StudyInstanceUID, ourStudy);
+        if (ourStudy.empty())
+        {
+            DCMIOD_ERROR("Could not add references: No Study Instance UID specified for \"this\" object");
+            return 0;
+        }
     }
-    else
+
+    const OFVector<IODReference*> refs          = references.get();
+    OFVector<IODReference*>::const_iterator ref = refs.begin();
+    size_t count                                = 0;
+    while (ref != refs.end())
     {
-      // Reference lies outside of "this" study, put it into Studies Containing
-      // Other Referenced Instances Sequence
-      OFVector<StudiesOtherInstancesItem*>::iterator it = m_StudiesContainingOtherReferencedInstancesSequence.begin();
-      while (it != m_StudiesContainingOtherReferencedInstancesSequence.end())
-      {
-        OFString studyEntry;
-        (*it)->getStudyInstanceUID(studyEntry);
-        if (studyEntry == refStudy)
+        OFCondition result;
+        // If reference belongs into "this" study, add it to Referenced Series Sequence
+        OFString refStudy = (*ref)->m_StudyInstanceUID;
+        if (refStudy == ourStudy)
         {
-          result = addSeriesReference(
-            (*it)->getReferencedSeriesAndInstanceReferences().getReferencedSeriesItems(),
-            **ref);
-          break;
+            result = addSeriesReference(m_ReferenceSeriesItems, **ref);
         }
         else
         {
-          it++;
-        }
-      }
-      // We did not find an entry for this study, add new one
-      if (it == m_StudiesContainingOtherReferencedInstancesSequence.end())
-      {
-        StudiesOtherInstancesItem* newItem = new StudiesOtherInstancesItem();
-        if (newItem)
-        {
-          result = newItem->setStudyInstanceUID(refStudy);
-          if (result.good())
-          {
-            result = addSeriesReference(newItem->getReferencedSeriesAndInstanceReferences().getReferencedSeriesItems(), **ref);
-          }
-          if (result.good())
-          {
-            m_StudiesContainingOtherReferencedInstancesSequence.push_back(newItem);
-          }
-          else
-          {
-            delete newItem;
-          }
+            // Reference lies outside of "this" study, put it into Studies Containing
+            // Other Referenced Instances Sequence
+            OFVector<StudiesOtherInstancesItem*>::iterator it
+                = m_StudiesContainingOtherReferencedInstancesSequence.begin();
+            while (it != m_StudiesContainingOtherReferencedInstancesSequence.end())
+            {
+                OFString studyEntry;
+                (*it)->getStudyInstanceUID(studyEntry);
+                if (studyEntry == refStudy)
+                {
+                    result = addSeriesReference(
+                        (*it)->getReferencedSeriesAndInstanceReferences().getReferencedSeriesItems(), **ref);
+                    break;
+                }
+                else
+                {
+                    it++;
+                }
+            }
+            // We did not find an entry for this study, add new one
+            if (it == m_StudiesContainingOtherReferencedInstancesSequence.end())
+            {
+                StudiesOtherInstancesItem* newItem = new StudiesOtherInstancesItem();
+                if (newItem)
+                {
+                    result = newItem->setStudyInstanceUID(refStudy);
+                    if (result.good())
+                    {
+                        result = addSeriesReference(
+                            newItem->getReferencedSeriesAndInstanceReferences().getReferencedSeriesItems(), **ref);
+                    }
+                    if (result.good())
+                    {
+                        m_StudiesContainingOtherReferencedInstancesSequence.push_back(newItem);
+                    }
+                    else
+                    {
+                        delete newItem;
+                    }
+                }
+                else
+                {
+                    DCMIOD_ERROR("Memory exhausted while adding references to Common Instance Reference Module");
+                    return count;
+                }
+            }
         }
-        else
+        if (result.good())
         {
-          DCMIOD_ERROR("Memory exhausted while adding references to Common Instance Reference Module");
-          return count;
+            count++;
         }
-      }
-    }
-    if (result.good())
-    {
-      count++;
+        ref++;
     }
-    ref++;
-  }
-  return count;
+    return count;
 }
 
-
 void IODCommonInstanceReferenceModule::resetRules()
 {
-  // Parameters for Rule are tag, VM, type (1,1C,2,2C,3), module name and logical IOD level
-  m_Rules->addRule(new IODRule(DCM_ReferencedSeriesSequence, "1-n", "1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_StudiesContainingOtherReferencedInstancesSequence, "1-n", "1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    // Parameters for Rule are tag, VM, type (1,1C,2,2C,3), module name and logical IOD level
+    m_Rules->addRule(new IODRule(DCM_ReferencedSeriesSequence, "1-n", "1C", getName(), DcmIODTypes::IE_INSTANCE),
+                     OFTrue);
+    m_Rules->addRule(
+        new IODRule(
+            DCM_StudiesContainingOtherReferencedInstancesSequence, "1-n", "1C", getName(), DcmIODTypes::IE_INSTANCE),
+        OFTrue);
 }
 
-
 OFCondition IODCommonInstanceReferenceModule::addSeriesReference(
-  OFVector<IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem*>& container,
-  const IODReference& ref)
+    OFVector<IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem*>& container, const IODReference& ref)
 {
-  OFCondition result;
-  OFVector<IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem*>::iterator series = container.begin();
-  while ( series != container.end() )
-  {
-    OFString s;
-    (*series)->getSeriesInstanceUID(s);
-    if (s == ref.m_SeriesInstanceUID)
-    {
-      // There is already an entry for this series
-      result = (*series)->addReference(ref.m_SOPClassUID, ref.m_SOPInstanceUID);
-      if (result.good())
-      {
-        return EC_Normal;
-      }
-      else
-      {
-        DCMIOD_ERROR("Could not add reference to Common Instance Reference Module: " << ref.toString());
-        return IOD_EC_InvalidElementValue;
-      }
-    }
-    series++;
-  }
-  // If we do not have such a series Referenced Series Sequence, add it
-  if (series == container.end())
-  {
-    IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem* newseries = new IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem();
-    if (!newseries)
-    {
-      return EC_MemoryExhausted;
-    }
-    result = newseries->setSeriesInstanceUID( ref.m_SeriesInstanceUID);
-    if (result.good()) result = newseries->addReference(ref.m_SOPClassUID, ref.m_SOPInstanceUID);
-    if (result.good())
+    OFCondition result;
+    OFVector<IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem*>::iterator series = container.begin();
+    while (series != container.end())
     {
-      container.push_back(newseries);
+        OFString s;
+        (*series)->getSeriesInstanceUID(s);
+        if (s == ref.m_SeriesInstanceUID)
+        {
+            // There is already an entry for this series
+            result = (*series)->addReference(ref.m_SOPClassUID, ref.m_SOPInstanceUID);
+            if (result.good())
+            {
+                return EC_Normal;
+            }
+            else
+            {
+                DCMIOD_ERROR("Could not add reference to Common Instance Reference Module: " << ref.toString());
+                return IOD_EC_InvalidElementValue;
+            }
+        }
+        series++;
     }
-    else
+    // If we do not have such a series Referenced Series Sequence, add it
+    if (series == container.end())
     {
-      DCMIOD_ERROR("Could not add reference to Common Instance Reference Module: " << ref.toString());
+        IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem* newseries
+            = new IODSeriesAndInstanceReferenceMacro::ReferencedSeriesItem();
+        if (!newseries)
+        {
+            return EC_MemoryExhausted;
+        }
+        result = newseries->setSeriesInstanceUID(ref.m_SeriesInstanceUID);
+        if (result.good())
+            result = newseries->addReference(ref.m_SOPClassUID, ref.m_SOPInstanceUID);
+        if (result.good())
+        {
+            container.push_back(newseries);
+        }
+        else
+        {
+            DCMIOD_ERROR("Could not add reference to Common Instance Reference Module: " << ref.toString());
+        }
     }
-  }
-  return result;
+    return result;
 }
 
-
 // -- IODCommonInstanceReferenceModule::StudiesOtherInstancesItem --
 
-
-IODCommonInstanceReferenceModule::StudiesOtherInstancesItem::StudiesOtherInstancesItem(OFshared_ptr< DcmItem > item,
-                                                                                       OFshared_ptr< IODRules > rules,
+IODCommonInstanceReferenceModule::StudiesOtherInstancesItem::StudiesOtherInstancesItem(OFshared_ptr<DcmItem> item,
+                                                                                       OFshared_ptr<IODRules> rules,
                                                                                        IODComponent* parent)
-: IODComponent(item, rules, parent),
-  m_ReferencedSeriesAndInstance()
+    : IODComponent(item, rules, parent)
+    , m_ReferencedSeriesAndInstance()
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODCommonInstanceReferenceModule::StudiesOtherInstancesItem::StudiesOtherInstancesItem(IODComponent* parent)
-: IODComponent(parent),
-  m_ReferencedSeriesAndInstance()
+    : IODComponent(parent)
+    , m_ReferencedSeriesAndInstance()
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODCommonInstanceReferenceModule::StudiesOtherInstancesItem::~StudiesOtherInstancesItem()
 {
-  clearData();
+    clearData();
 }
 
-
-
 OFString IODCommonInstanceReferenceModule::StudiesOtherInstancesItem::getName() const
 {
-  return m_ComponentName;
+    return m_ComponentName;
 }
 
-
 void IODCommonInstanceReferenceModule::StudiesOtherInstancesItem::clearData()
 {
-  m_ReferencedSeriesAndInstance.clearData();
-  IODComponent::clearData();
+    m_ReferencedSeriesAndInstance.clearData();
+    IODComponent::clearData();
 }
 
-
 OFCondition IODCommonInstanceReferenceModule::StudiesOtherInstancesItem::read(DcmItem& source,
                                                                               const OFBool clearOldData)
 {
-  if (clearOldData)
-    clearData();
+    if (clearOldData)
+        clearData();
 
-  IODComponent::read(source, clearOldData);
-  m_ReferencedSeriesAndInstance.read(source, clearOldData);
-  return EC_Normal;
+    IODComponent::read(source, clearOldData);
+    m_ReferencedSeriesAndInstance.read(source, clearOldData);
+    return EC_Normal;
 }
 
-
 OFCondition IODCommonInstanceReferenceModule::StudiesOtherInstancesItem::write(DcmItem& destination)
 {
-  OFCondition result = EC_Normal;
-  result = IODComponent::write(destination);
+    OFCondition result = EC_Normal;
+    result             = IODComponent::write(destination);
 
-  if (result.good()) result = m_ReferencedSeriesAndInstance.write(destination);
+    if (result.good())
+        result = m_ReferencedSeriesAndInstance.write(destination);
 
-  return result;
+    return result;
 }
 
-
 void IODCommonInstanceReferenceModule::StudiesOtherInstancesItem::resetRules()
 {
-  // Parameters for Rule are tag, VM, type (1,1C,2,2C,3), module name and logical IOD level
-  m_Rules->addRule(new IODRule(DCM_StudyInstanceUID, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    // Parameters for Rule are tag, VM, type (1,1C,2,2C,3), module name and logical IOD level
+    m_Rules->addRule(new IODRule(DCM_StudyInstanceUID, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
 }
 
-
-IODSeriesAndInstanceReferenceMacro& IODCommonInstanceReferenceModule::StudiesOtherInstancesItem::getReferencedSeriesAndInstanceReferences()
+IODSeriesAndInstanceReferenceMacro&
+IODCommonInstanceReferenceModule::StudiesOtherInstancesItem::getReferencedSeriesAndInstanceReferences()
 {
-  return m_ReferencedSeriesAndInstance;
+    return m_ReferencedSeriesAndInstance;
 }
 
-
-OFCondition IODCommonInstanceReferenceModule::StudiesOtherInstancesItem::getStudyInstanceUID(OFString& value,
-                                                                                             const long signed int pos) const
+OFCondition
+IODCommonInstanceReferenceModule::StudiesOtherInstancesItem::getStudyInstanceUID(OFString& value,
+                                                                                 const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_StudyInstanceUID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_StudyInstanceUID, *m_Item, value, pos);
 }
 
-
 OFCondition IODCommonInstanceReferenceModule::StudiesOtherInstancesItem::setStudyInstanceUID(const OFString& value,
-                                                                                             const bool checkValue)
+                                                                                             const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_StudyInstanceUID, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_StudyInstanceUID, value);
+    return result;
 }
 
-
 void IODCommonInstanceReferenceModule::freeMemory()
 {
-  DcmIODUtil::freeContainer(m_StudiesContainingOtherReferencedInstancesSequence);
-  DcmIODUtil::freeContainer(m_ReferenceSeriesItems);
+    DcmIODUtil::freeContainer(m_StudiesContainingOtherReferencedInstancesSequence);
+    DcmIODUtil::freeContainer(m_ReferenceSeriesItems);
 }
index 6c834cdba66989558c69227f1013f21a4073c999..33c7333a53f587aa07db8e2f9b53985b0a4cdeea 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modenhequipment.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmdata/dcdeftag.h"
 #include "dcmtk/dcmdata/dcvrlo.h"
-#include "dcmtk/dcmdata/dcvrst.h"
 #include "dcmtk/dcmdata/dcvrsh.h"
+#include "dcmtk/dcmdata/dcvrst.h"
 #include "dcmtk/dcmiod/iodutil.h"
 
-IODEnhGeneralEquipmentModule::IODEnhGeneralEquipmentModule(OFshared_ptr<DcmItem> item,
-                                                           OFshared_ptr<IODRules> rules)
-: IODModule(item, rules),
-  m_ModuleName("EnhancedGeneralEquipmentModule")
+IODEnhGeneralEquipmentModule::IODEnhGeneralEquipmentModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODModule(item, rules)
+    , m_ModuleName("EnhancedGeneralEquipmentModule")
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODEnhGeneralEquipmentModule::IODEnhGeneralEquipmentModule()
-: IODModule(),
-  m_ModuleName("EnhancedGeneralEquipmentModule")
+    : IODModule()
+    , m_ModuleName("EnhancedGeneralEquipmentModule")
 {
-  resetRules();
+    resetRules();
 }
 
-
 OFCondition IODEnhGeneralEquipmentModule::create(const IODEnhGeneralEquipmentModule::EquipmentInfo& info,
                                                  IODEnhGeneralEquipmentModule* equipment)
 {
-  equipment = new IODEnhGeneralEquipmentModule();
-  if (!equipment)
-  {
-    return EC_MemoryExhausted;
-  }
-  return equipment->set(info);
+    equipment = new IODEnhGeneralEquipmentModule();
+    if (!equipment)
+    {
+        return EC_MemoryExhausted;
+    }
+    return equipment->set(info);
 }
 
-
 void IODEnhGeneralEquipmentModule::resetRules()
 {
-  m_Rules->addRule(new IODRule(DCM_Manufacturer, "1", "1", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ManufacturerModelName, "1", "1", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_DeviceSerialNumber, "1", "1", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_SoftwareVersions, "1-n", "1", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_Manufacturer, "1", "1", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ManufacturerModelName, "1", "1", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_DeviceSerialNumber, "1", "1", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_SoftwareVersions, "1-n", "1", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
 }
 
-
 IODEnhGeneralEquipmentModule::~IODEnhGeneralEquipmentModule()
 {
-  // Nothing to do
+    // Nothing to do
 }
 
-
 OFString IODEnhGeneralEquipmentModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
-OFCondition IODEnhGeneralEquipmentModule::getDeviceSerialNumber(OFString& value,
-                                                                 const long signed int pos) const
+OFCondition IODEnhGeneralEquipmentModule::getDeviceSerialNumber(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_DeviceSerialNumber, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_DeviceSerialNumber, *m_Item, value, pos);
 }
 
-
-OFCondition IODEnhGeneralEquipmentModule::getManufacturer(OFString& value,
-                                                          const long signed int pos) const
+OFCondition IODEnhGeneralEquipmentModule::getManufacturer(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_Manufacturer, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_Manufacturer, *m_Item, value, pos);
 }
 
-
-OFCondition IODEnhGeneralEquipmentModule::getManufacturerModelName(OFString& value,
-                                                                   const long signed int pos) const
+OFCondition IODEnhGeneralEquipmentModule::getManufacturerModelName(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_ManufacturerModelName, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_ManufacturerModelName, *m_Item, value, pos);
 }
 
-
-OFCondition IODEnhGeneralEquipmentModule::getSoftwareVersions(OFString& value,
-                                                              const long signed int pos) const
+OFCondition IODEnhGeneralEquipmentModule::getSoftwareVersions(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_SoftwareVersions, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_SoftwareVersions, *m_Item, value, pos);
 }
 
-
-OFCondition IODEnhGeneralEquipmentModule::setDeviceSerialNumber(const OFString& value,
-                                                                const OFBool checkValue)
+OFCondition IODEnhGeneralEquipmentModule::setDeviceSerialNumber(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_DeviceSerialNumber, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_DeviceSerialNumber, value);
+    return result;
 }
 
-
-OFCondition IODEnhGeneralEquipmentModule::setManufacturer(const OFString& value,
-                                                          const OFBool checkValue)
+OFCondition IODEnhGeneralEquipmentModule::setManufacturer(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_Manufacturer, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_Manufacturer, value);
+    return result;
 }
 
-
-OFCondition IODEnhGeneralEquipmentModule::setManufacturerModelName(const OFString& value,
-                                                                   const OFBool checkValue)
+OFCondition IODEnhGeneralEquipmentModule::setManufacturerModelName(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_ManufacturerModelName, value);
-  return result;
-
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_ManufacturerModelName, value);
+    return result;
 }
 
-
-OFCondition IODEnhGeneralEquipmentModule::setSoftwareVersions(const OFString& value,
-                                                              const OFBool checkValue)
+OFCondition IODEnhGeneralEquipmentModule::setSoftwareVersions(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1-n") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_SoftwareVersions, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1-n") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_SoftwareVersions, value);
+    return result;
 }
 
-
 OFCondition IODEnhGeneralEquipmentModule::set(const IODEnhGeneralEquipmentModule::EquipmentInfo& info)
 {
-  if (info.m_DeviceSerialNumber.empty() || info.m_Manufacturer.empty() ||
-    info.m_ManufacturerModelName.empty() || info.m_SoftwareVersions.empty())
-    return IOD_EC_InvalidElementValue;
-
-  OFCondition result = setManufacturer(info.m_Manufacturer);
-  if (result.good()) result = setManufacturerModelName(info.m_ManufacturerModelName);
-  if (result.good()) result = setDeviceSerialNumber(info.m_DeviceSerialNumber);
-  if (result.good()) result = setSoftwareVersions(info.m_SoftwareVersions);
-  return result;
+    if (info.m_DeviceSerialNumber.empty() || info.m_Manufacturer.empty() || info.m_ManufacturerModelName.empty()
+        || info.m_SoftwareVersions.empty())
+        return IOD_EC_InvalidElementValue;
+
+    OFCondition result = setManufacturer(info.m_Manufacturer);
+    if (result.good())
+        result = setManufacturerModelName(info.m_ManufacturerModelName);
+    if (result.good())
+        result = setDeviceSerialNumber(info.m_DeviceSerialNumber);
+    if (result.good())
+        result = setSoftwareVersions(info.m_SoftwareVersions);
+    return result;
 }
index 7cb42a7825fb3d8e7912677fc77a1d9ed6ae9d64..3aec0dabaf842099315c088b39c6fc65015bcacd 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2017, Open Connections GmbH
+ *  Copyright (C) 2015-2020, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modenhusimage.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/iodutil.h"
 
 const OFString IODEnhUSImageModule::m_ModuleName = "EnhancedUSImageModule";
 
-
-IODEnhUSImageModule::IODEnhUSImageModule(OFshared_ptr<DcmItem> item,
-                                         OFshared_ptr<IODRules> rules)
-: IODModule(item, rules),
-  m_MandatoryViewAndSliceProgressionDirection(),
-  m_Anatomy("1" /* mandatory version */),
-  m_TransducerScanPattern(),
-  m_TransducerGeometry(),
-  m_TransducerBeamSteering(),
-  m_TransducerApplication()
+IODEnhUSImageModule::IODEnhUSImageModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODModule(item, rules)
+    , m_MandatoryViewAndSliceProgressionDirection()
+    , m_Anatomy("1" /* mandatory version */)
+    , m_TransducerScanPattern()
+    , m_TransducerGeometry()
+    , m_TransducerBeamSteering()
+    , m_TransducerApplication()
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODEnhUSImageModule::IODEnhUSImageModule()
-: IODModule(),
-  m_MandatoryViewAndSliceProgressionDirection(),
-  m_Anatomy("1" /* mandatory version */),
-  m_TransducerScanPattern(),
-  m_TransducerGeometry(),
-  m_TransducerBeamSteering(),
-  m_TransducerApplication()
+    : IODModule()
+    , m_MandatoryViewAndSliceProgressionDirection()
+    , m_Anatomy("1" /* mandatory version */)
+    , m_TransducerScanPattern()
+    , m_TransducerGeometry()
+    , m_TransducerBeamSteering()
+    , m_TransducerApplication()
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 OFString IODEnhUSImageModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 void IODEnhUSImageModule::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_ImageType, "4","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_SamplesPerPixel, "1","1" ,getName(), DcmIODTypes::IE_IMAGE, "1"), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PhotometricInterpretation, "1","1" ,getName(), DcmIODTypes::IE_IMAGE, "MONOCHROME2"), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_Rows, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_Columns, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_BitsAllocated, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_BitsStored, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_HighBit, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PixelRepresentation, "1","1" ,getName(), DcmIODTypes::IE_IMAGE, "0"), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_DimensionOrganizationType, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_AcquisitionDateTime, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_AcquisitionDuration, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PixelSpacing, "2","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PositionMeasuringDeviceUsed, "1","1C" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_LossyImageCompression, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_LossyImageCompressionRatio, "1-n","1C" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_LossyImageCompressionMethod, "1-n","1C" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PresentationLUTShape, "1","1" ,getName(), DcmIODTypes::IE_IMAGE, "IDENTITY"), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_RescaleSlope, "1","1" ,getName(), DcmIODTypes::IE_IMAGE, "1"), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_RescaleIntercept, "1","1" ,getName(), DcmIODTypes::IE_IMAGE, "0"), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_BurnedInAnnotation, "1","1" ,getName(), DcmIODTypes::IE_IMAGE, "NO"), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_RecognizableVisualFeatures, "1","3" ,getName(), DcmIODTypes::IE_IMAGE, "NO"), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_TransducerScanPatternCodeSequence, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_TransducerGeometryCodeSequence, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_TransducerBeamSteeringCodeSequence, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_TransducerApplicationCodeSequence, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ProcessingFunction, "1","3" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_MechanicalIndex, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_BoneThermalIndex, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_CranialThermalIndex, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_SoftTissueThermalIndex, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_DepthsOfFocus, "1-n","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_DepthOfScanField, "1","1" ,getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_ImageType, "4", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_SamplesPerPixel, "1", "1", getName(), DcmIODTypes::IE_IMAGE, "1"), OFTrue);
+    m_Rules->addRule(
+        new IODRule(DCM_PhotometricInterpretation, "1", "1", getName(), DcmIODTypes::IE_IMAGE, "MONOCHROME2"), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_Rows, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_Columns, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_BitsAllocated, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_BitsStored, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_HighBit, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PixelRepresentation, "1", "1", getName(), DcmIODTypes::IE_IMAGE, "0"), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_DimensionOrganizationType, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_AcquisitionDateTime, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_AcquisitionDuration, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PixelSpacing, "2", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PositionMeasuringDeviceUsed, "1", "1C", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_LossyImageCompression, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_LossyImageCompressionRatio, "1-n", "1C", getName(), DcmIODTypes::IE_IMAGE),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_LossyImageCompressionMethod, "1-n", "1C", getName(), DcmIODTypes::IE_IMAGE),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PresentationLUTShape, "1", "1", getName(), DcmIODTypes::IE_IMAGE, "IDENTITY"),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_RescaleSlope, "1", "1", getName(), DcmIODTypes::IE_IMAGE, "1"), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_RescaleIntercept, "1", "1", getName(), DcmIODTypes::IE_IMAGE, "0"), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_BurnedInAnnotation, "1", "1", getName(), DcmIODTypes::IE_IMAGE, "NO"), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_RecognizableVisualFeatures, "1", "3", getName(), DcmIODTypes::IE_IMAGE, "NO"),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_TransducerScanPatternCodeSequence, "1", "1", getName(), DcmIODTypes::IE_IMAGE),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_TransducerGeometryCodeSequence, "1", "1", getName(), DcmIODTypes::IE_IMAGE),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_TransducerBeamSteeringCodeSequence, "1", "1", getName(), DcmIODTypes::IE_IMAGE),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_TransducerApplicationCodeSequence, "1", "1", getName(), DcmIODTypes::IE_IMAGE),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ProcessingFunction, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_MechanicalIndex, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_BoneThermalIndex, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_CranialThermalIndex, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_SoftTissueThermalIndex, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_DepthsOfFocus, "1-n", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_DepthOfScanField, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
 }
 
-
 IODEnhUSImageModule::~IODEnhUSImageModule()
 {
-  DcmIODUtil::freeContainer(m_TransducerBeamSteering);
+    DcmIODUtil::freeContainer(m_TransducerBeamSteering);
 }
 
-
-OFCondition IODEnhUSImageModule::read(DcmItem& source,
-                                      const OFBool clearOldData)
+OFCondition IODEnhUSImageModule::read(DcmItem& source, const OFBool clearOldData)
 {
-  if (clearOldData)
-  {
-    DcmIODUtil::freeContainer(m_TransducerBeamSteering);
-  }
-  m_MandatoryViewAndSliceProgressionDirection.read(source, clearOldData);
-  m_Anatomy.read(source, clearOldData);
-  DcmIODUtil::readSingleItem(source, DCM_TransducerApplicationCodeSequence, m_TransducerApplication, m_Rules->getByTag(DCM_TransducerApplicationCodeSequence));
-  DcmIODUtil::readSingleItem(source, DCM_TransducerGeometryCodeSequence, m_TransducerGeometry, m_Rules->getByTag(DCM_TransducerGeometryCodeSequence));
-  DcmIODUtil::readSingleItem(source, DCM_TransducerScanPatternCodeSequence, m_TransducerGeometry, m_Rules->getByTag(DCM_TransducerScanPatternCodeSequence));
-  DcmIODUtil::readSubSequence(source, DCM_TransducerBeamSteeringCodeSequence, m_TransducerBeamSteering, m_Rules->getByTag(DCM_TransducerBeamSteeringCodeSequence));
-  IODComponent::read(source, clearOldData);
-  return EC_Normal;
+    if (clearOldData)
+    {
+        DcmIODUtil::freeContainer(m_TransducerBeamSteering);
+    }
+    m_MandatoryViewAndSliceProgressionDirection.read(source, clearOldData);
+    m_Anatomy.read(source, clearOldData);
+    DcmIODUtil::readSingleItem(source,
+                               DCM_TransducerApplicationCodeSequence,
+                               m_TransducerApplication,
+                               m_Rules->getByTag(DCM_TransducerApplicationCodeSequence));
+    DcmIODUtil::readSingleItem(source,
+                               DCM_TransducerGeometryCodeSequence,
+                               m_TransducerGeometry,
+                               m_Rules->getByTag(DCM_TransducerGeometryCodeSequence));
+    DcmIODUtil::readSingleItem(source,
+                               DCM_TransducerScanPatternCodeSequence,
+                               m_TransducerScanPattern,
+                               m_Rules->getByTag(DCM_TransducerScanPatternCodeSequence));
+    DcmIODUtil::readSubSequence(source,
+                                DCM_TransducerBeamSteeringCodeSequence,
+                                m_TransducerBeamSteering,
+                                m_Rules->getByTag(DCM_TransducerBeamSteeringCodeSequence));
+    IODComponent::read(source, clearOldData);
+    return EC_Normal;
 }
 
-
-
 OFCondition IODEnhUSImageModule::write(DcmItem& destination)
 {
-  OFCondition result;
+    OFCondition result;
 
-  // Copy sequences to source (which then will be later copied to destination by IODComponent::write()
-  result = m_MandatoryViewAndSliceProgressionDirection.write(destination);
-  if (result.good()) result = m_Anatomy.write(destination);
-  DcmIODUtil::writeSingleItem(result, DCM_TransducerScanPatternCodeSequence, m_TransducerScanPattern, *m_Item, m_Rules->getByTag(DCM_TransducerScanPatternCodeSequence));
-  DcmIODUtil::writeSingleItem(result, DCM_TransducerGeometryCodeSequence, m_TransducerGeometry, *m_Item, m_Rules->getByTag(DCM_TransducerGeometryCodeSequence));
-  DcmIODUtil::writeSingleItem(result, DCM_TransducerApplicationCodeSequence, m_TransducerApplication, *m_Item, m_Rules->getByTag(DCM_TransducerApplicationCodeSequence));
-  DcmIODUtil::writeSubSequence(result, DCM_TransducerBeamSteeringCodeSequence, m_TransducerBeamSteering, *m_Item, m_Rules->getByTag(DCM_TransducerBeamSteeringCodeSequence));
-  if (result.good()) result = IODComponent::write(destination);
-  return result;
+    // Copy sequences to source (which then will be later copied to destination by IODComponent::write()
+    result = m_MandatoryViewAndSliceProgressionDirection.write(destination);
+    if (result.good())
+        result = m_Anatomy.write(destination);
+    DcmIODUtil::writeSingleItem(result,
+                                DCM_TransducerScanPatternCodeSequence,
+                                m_TransducerScanPattern,
+                                *m_Item,
+                                m_Rules->getByTag(DCM_TransducerScanPatternCodeSequence));
+    DcmIODUtil::writeSingleItem(result,
+                                DCM_TransducerGeometryCodeSequence,
+                                m_TransducerGeometry,
+                                *m_Item,
+                                m_Rules->getByTag(DCM_TransducerGeometryCodeSequence));
+    DcmIODUtil::writeSingleItem(result,
+                                DCM_TransducerApplicationCodeSequence,
+                                m_TransducerApplication,
+                                *m_Item,
+                                m_Rules->getByTag(DCM_TransducerApplicationCodeSequence));
+    DcmIODUtil::writeSubSequence(result,
+                                 DCM_TransducerBeamSteeringCodeSequence,
+                                 m_TransducerBeamSteering,
+                                 *m_Item,
+                                 m_Rules->getByTag(DCM_TransducerBeamSteeringCodeSequence));
+    if (result.good())
+        result = IODComponent::write(destination);
+    return result;
 }
 
-
 // --- get attributes (C++ string) ---
 
-
-OFCondition IODEnhUSImageModule::getImageType(OFString& value,
-                                              const signed long pos)
+OFCondition IODEnhUSImageModule::getImageType(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_ImageType, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_ImageType, *m_Item, value, pos);
 }
 
-
-
-OFCondition IODEnhUSImageModule::getSamplesPerPixel(Uint16& value,
-                                                    const unsigned long pos)
+OFCondition IODEnhUSImageModule::getSamplesPerPixel(Uint16& value, const unsigned long pos)
 {
-  return m_Item->findAndGetUint16(DCM_SamplesPerPixel, value, pos);
+    return m_Item->findAndGetUint16(DCM_SamplesPerPixel, value, pos);
 }
 
-
-
-OFCondition IODEnhUSImageModule::getPhotometricInterpretation(OFString& value,
-                                                              const signed long pos)
+OFCondition IODEnhUSImageModule::getPhotometricInterpretation(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_PhotometricInterpretation, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_PhotometricInterpretation, *m_Item, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getRows(Uint16& value,
-                                         const unsigned long pos)
+OFCondition IODEnhUSImageModule::getRows(Uint16& value, const unsigned long pos)
 {
-  return m_Item->findAndGetUint16(DCM_Rows, value, pos);
+    return m_Item->findAndGetUint16(DCM_Rows, value, pos);
 }
 
-
-
-OFCondition IODEnhUSImageModule::getColumns(Uint16& value,
-                                            const unsigned long pos)
+OFCondition IODEnhUSImageModule::getColumns(Uint16& value, const unsigned long pos)
 {
-  return m_Item->findAndGetUint16(DCM_Columns, value, pos);
+    return m_Item->findAndGetUint16(DCM_Columns, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getBitsAllocated(Uint16& value,
-                                                  const unsigned long pos)
+OFCondition IODEnhUSImageModule::getBitsAllocated(Uint16& value, const unsigned long pos)
 {
-  return m_Item->findAndGetUint16(DCM_BitsAllocated, value, pos);
+    return m_Item->findAndGetUint16(DCM_BitsAllocated, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getBitsStored(Uint16& value,
-                                               const unsigned long pos)
+OFCondition IODEnhUSImageModule::getBitsStored(Uint16& value, const unsigned long pos)
 {
-  return m_Item->findAndGetUint16(DCM_BitsStored, value, pos);
+    return m_Item->findAndGetUint16(DCM_BitsStored, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getHighBit(Uint16& value,
-                                            const unsigned long pos)
+OFCondition IODEnhUSImageModule::getHighBit(Uint16& value, const unsigned long pos)
 {
-  return m_Item->findAndGetUint16(DCM_HighBit, value, pos);
+    return m_Item->findAndGetUint16(DCM_HighBit, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getPixelRepresentation(Uint16& value,
-                                                        const unsigned long pos)
+OFCondition IODEnhUSImageModule::getPixelRepresentation(Uint16& value, const unsigned long pos)
 {
-  return m_Item->findAndGetUint16(DCM_PixelRepresentation, value, pos);
+    return m_Item->findAndGetUint16(DCM_PixelRepresentation, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getDimensionOrganizationType(OFString& value,
-                                                              const signed long pos)
+OFCondition IODEnhUSImageModule::getDimensionOrganizationType(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_DimensionOrganizationType, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_DimensionOrganizationType, *m_Item, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getAcquisitionDateTime(OFString& value,
-                                                        const signed long pos)
+OFCondition IODEnhUSImageModule::getAcquisitionDateTime(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_AcquisitionDateTime, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_AcquisitionDateTime, *m_Item, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getAcquisitionDuration(Float64& value,
-                                                        const unsigned long pos)
+OFCondition IODEnhUSImageModule::getAcquisitionDuration(Float64& value, const unsigned long pos)
 {
-  return m_Item->findAndGetFloat64(DCM_AcquisitionDuration, value, pos);
+    return m_Item->findAndGetFloat64(DCM_AcquisitionDuration, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getPixelSpacing(Float64& value,
-                                                 const unsigned long pos)
+OFCondition IODEnhUSImageModule::getPixelSpacing(Float64& value, const unsigned long pos)
 {
-  return m_Item->findAndGetFloat64(DCM_PixelSpacing, value, pos);
+    return m_Item->findAndGetFloat64(DCM_PixelSpacing, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getPositionMeasuringDevice(OFString& value,
-                                                            const signed long pos)
+OFCondition IODEnhUSImageModule::getPositionMeasuringDevice(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_PositionMeasuringDeviceUsed, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_PositionMeasuringDeviceUsed, *m_Item, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getLossyImageCompression(OFString& value,
-                                                          const signed long pos)
+OFCondition IODEnhUSImageModule::getLossyImageCompression(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_LossyImageCompression, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_LossyImageCompression, *m_Item, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getLossyImageCompressionRatio(Float64& value,
-                                                               const unsigned long pos)
+OFCondition IODEnhUSImageModule::getLossyImageCompressionRatio(Float64& value, const unsigned long pos)
 {
-  return m_Item->findAndGetFloat64(DCM_LossyImageCompressionRatio, value, pos);
+    return m_Item->findAndGetFloat64(DCM_LossyImageCompressionRatio, value, pos);
 }
 
-
 OFCondition IODEnhUSImageModule::getLossyImageCompressionMethod(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_LossyImageCompressionMethod, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_LossyImageCompressionMethod, *m_Item, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getPresentationLUTShape(OFString& value,
-                                                         const signed long pos)
+OFCondition IODEnhUSImageModule::getPresentationLUTShape(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_PresentationLUTShape, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_PresentationLUTShape, *m_Item, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getRescaleSlope(Float64& value,
-                                                 const unsigned long pos)
+OFCondition IODEnhUSImageModule::getRescaleSlope(Float64& value, const unsigned long pos)
 {
-  return m_Item->findAndGetFloat64(DCM_RescaleSlope, value, pos);
+    return m_Item->findAndGetFloat64(DCM_RescaleSlope, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getRescaleIntercept(OFString& value,
-                                                     const signed long pos)
+OFCondition IODEnhUSImageModule::getRescaleIntercept(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_RescaleSlope, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_RescaleSlope, *m_Item, value, pos);
 }
 
-
 GeneralAnatomyMacro& IODEnhUSImageModule::getAnatomy()
 {
-  return m_Anatomy;
+    return m_Anatomy;
 }
 
-
 MandatoryViewAndSliceProgressionDirectionMacro& IODEnhUSImageModule::getMandatoryViewAndSliceProgressionDirection()
 {
-  return m_MandatoryViewAndSliceProgressionDirection;
+    return m_MandatoryViewAndSliceProgressionDirection;
 }
 
-
-OFCondition IODEnhUSImageModule::getBurnedInAnnotation(OFString& value,
-                                                       const signed long pos)
+OFCondition IODEnhUSImageModule::getBurnedInAnnotation(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_BurnedInAnnotation, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_BurnedInAnnotation, *m_Item, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getRecognizableVisibleFeatures(OFString& value,
-                                                                const signed long pos)
+OFCondition IODEnhUSImageModule::getRecognizableVisibleFeatures(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_RecognizableVisualFeatures, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_RecognizableVisualFeatures, *m_Item, value, pos);
 }
 
-
 CodeSequenceMacro& IODEnhUSImageModule::getTransducerScanPattern()
 {
-  return m_TransducerScanPattern;
+    return m_TransducerScanPattern;
 }
 
-
 CodeSequenceMacro& IODEnhUSImageModule::getTransducerGeometry()
 {
-  return m_TransducerGeometry;
+    return m_TransducerGeometry;
 }
 
-
 OFVector<CodeSequenceMacro*>& IODEnhUSImageModule::getTransducerBeamSteering()
 {
-  return m_TransducerBeamSteering;
+    return m_TransducerBeamSteering;
 }
 
-
 CodeSequenceMacro& IODEnhUSImageModule::getTransducerApplication()
 {
-  return m_TransducerApplication;
+    return m_TransducerApplication;
 }
 
-
-OFCondition IODEnhUSImageModule::getProcessingFunction(OFString& value,
-                                                       const signed long pos)
+OFCondition IODEnhUSImageModule::getProcessingFunction(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_ProcessingFunction, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_ProcessingFunction, *m_Item, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getMechanicalIndex(Float64& value,
-                                                    const unsigned long pos)
+OFCondition IODEnhUSImageModule::getMechanicalIndex(Float64& value, const unsigned long pos)
 {
-  return m_Item->findAndGetFloat64(DCM_MechanicalIndex, value, pos);
+    return m_Item->findAndGetFloat64(DCM_MechanicalIndex, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getBoneThermalIndex(Float64& value,
-                                                     const unsigned long pos)
+OFCondition IODEnhUSImageModule::getBoneThermalIndex(Float64& value, const unsigned long pos)
 {
-  return m_Item->findAndGetFloat64(DCM_BoneThermalIndex, value, pos);
+    return m_Item->findAndGetFloat64(DCM_BoneThermalIndex, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getCranialThermalIndex(Float64& value,
-                                                        const unsigned long pos)
+OFCondition IODEnhUSImageModule::getCranialThermalIndex(Float64& value, const unsigned long pos)
 {
-  return m_Item->findAndGetFloat64(DCM_CranialThermalIndex, value, pos);
+    return m_Item->findAndGetFloat64(DCM_CranialThermalIndex, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getSoftTissueThermalIndex(Float64& value,
-                                                           const unsigned long pos)
+OFCondition IODEnhUSImageModule::getSoftTissueThermalIndex(Float64& value, const unsigned long pos)
 {
-  return m_Item->findAndGetFloat64(DCM_SoftTissueThermalIndex, value, pos);
+    return m_Item->findAndGetFloat64(DCM_SoftTissueThermalIndex, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getDepthsOfFocus(Float64& value,
-                                                  const unsigned long pos)
+OFCondition IODEnhUSImageModule::getDepthsOfFocus(Float64& value, const unsigned long pos)
 {
-  return m_Item->findAndGetFloat64(DCM_DepthsOfFocus, value, pos);
+    return m_Item->findAndGetFloat64(DCM_DepthsOfFocus, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::getDepthsOfScanField(Float64& value,
-                                                      const unsigned long pos)
+OFCondition IODEnhUSImageModule::getDepthsOfScanField(Sint32& value, const unsigned long pos)
 {
-  return m_Item->findAndGetFloat64(DCM_DepthsOfFocus, value, pos);
+    return m_Item->findAndGetSint32(DCM_DepthOfScanField, value, pos);
 }
 
-
 // --- set attributes ---
 
-
 OFCondition IODEnhUSImageModule::setImageType(const DcmIODTypes::IOD_ENHUSIMAGETYPE pixelDataChar,
                                               const OFString& imageFlavor,
                                               const OFString& derivedPixelContrast,
                                               const OFBool checkValue)
 {
-  OFString value;
-  switch (pixelDataChar)
-  {
-    case(DcmIODTypes::IMAGETYPE_ORIGINAL): value = "ORIGINAL\\PRIMARY\\"; break;
-    case(DcmIODTypes::IMAGETYPE_DERIVED) : value = "DERIVED\\PRIMARY\\"; break;
-    default: return IOD_EC_InvalidElementValue;
-  }
-  value += imageFlavor;
-  value += "\\";
-  value += derivedPixelContrast;
+    OFString value;
+    switch (pixelDataChar)
+    {
+        case (DcmIODTypes::IMAGETYPE_ORIGINAL):
+            value = "ORIGINAL\\PRIMARY\\";
+            break;
+        case (DcmIODTypes::IMAGETYPE_DERIVED):
+            value = "DERIVED\\PRIMARY\\";
+            break;
+        default:
+            return IOD_EC_InvalidElementValue;
+    }
+    value += imageFlavor;
+    value += "\\";
+    value += derivedPixelContrast;
 
-  OFCondition result;
-  if (checkValue)
-  {
-    result = DcmCodeString::checkStringValue(value, "2");
-  }
-  if (result.good())
-  {
-    result = m_Item->putAndInsertOFStringArray(DCM_ImageType, value);
-  }
-  return result;
+    OFCondition result;
+    if (checkValue)
+    {
+        result = DcmCodeString::checkStringValue(value, "2");
+    }
+    if (result.good())
+    {
+        result = m_Item->putAndInsertOFStringArray(DCM_ImageType, value);
+    }
+    return result;
 }
 
-
-OFCondition IODEnhUSImageModule::setRows(const Uint16 value,
-                                         const bool checkValue)
+OFCondition IODEnhUSImageModule::setRows(const Uint16 value, const OFBool checkValue)
 {
-  if (checkValue && (value == 0))
-    return IOD_EC_InvalidElementValue;
+    if (checkValue && (value == 0))
+        return IOD_EC_InvalidElementValue;
 
-  return m_Item->putAndInsertUint16(DCM_Rows, value);
+    return m_Item->putAndInsertUint16(DCM_Rows, value);
 }
 
-
-OFCondition IODEnhUSImageModule::setColumns(const Uint16 value,
-                                            const bool checkValue)
+OFCondition IODEnhUSImageModule::setColumns(const Uint16 value, const OFBool checkValue)
 {
-  if (checkValue && (value == 0))
-    return IOD_EC_InvalidElementValue;
+    if (checkValue && (value == 0))
+        return IOD_EC_InvalidElementValue;
 
-  return m_Item->putAndInsertUint16(DCM_Columns, value);
+    return m_Item->putAndInsertUint16(DCM_Columns, value);
 }
 
-
-OFCondition IODEnhUSImageModule::setBitsAllocated(const Uint16 value,
-                                                  const bool checkValue)
+OFCondition IODEnhUSImageModule::setBitsAllocated(const Uint16 value, const OFBool checkValue)
 {
-  if (checkValue && (value != 8) && (value != 16))
-    return IOD_EC_InvalidElementValue;
+    if (checkValue && (value != 8) && (value != 16))
+        return IOD_EC_InvalidElementValue;
 
-  return m_Item->putAndInsertUint16(DCM_BitsAllocated, value);
+    return m_Item->putAndInsertUint16(DCM_BitsAllocated, value);
 }
 
-
-OFCondition IODEnhUSImageModule::setBitsStored(const Uint16 value,
-                                               const bool checkValue)
+OFCondition IODEnhUSImageModule::setBitsStored(const Uint16 value, const OFBool checkValue)
 {
-  if (checkValue && (value != 8) && (value != 16))
-    return IOD_EC_InvalidElementValue;
+    if (checkValue && (value != 8) && (value != 16))
+        return IOD_EC_InvalidElementValue;
 
-  return m_Item->putAndInsertUint16(DCM_BitsStored, value);
+    return m_Item->putAndInsertUint16(DCM_BitsStored, value);
 }
 
-
-OFCondition IODEnhUSImageModule::setHighBit(const Uint16 value,
-                                            const bool checkValue)
+OFCondition IODEnhUSImageModule::setHighBit(const Uint16 value, const OFBool checkValue)
 {
-  if (checkValue && (value != 7) && (value != 15))
-    return IOD_EC_InvalidElementValue;
+    if (checkValue && (value != 7) && (value != 15))
+        return IOD_EC_InvalidElementValue;
 
-  return m_Item->putAndInsertUint16(DCM_HighBit, value);
+    return m_Item->putAndInsertUint16(DCM_HighBit, value);
 }
 
-
-OFCondition IODEnhUSImageModule::setDimensionOrganizationType(const OFString& value,
-                                                              const bool checkValue)
+OFCondition IODEnhUSImageModule::setDimensionOrganizationType(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result;
-  if (checkValue)
-  {
-    if ( (value != "3D") && (value != "3D_TEMPORAL") )
-      return IOD_EC_InvalidElementValue;
-  }
-  return m_Item->putAndInsertOFStringArray(DCM_DimensionOrganizationType, value);
+    OFCondition result;
+    if (checkValue)
+    {
+        if ((value != "3D") && (value != "3D_TEMPORAL"))
+            return IOD_EC_InvalidElementValue;
+    }
+    return m_Item->putAndInsertOFStringArray(DCM_DimensionOrganizationType, value);
 }
 
-
-OFCondition IODEnhUSImageModule::setAcquisitionDateTime(const OFString& value,
-                                                        const OFBool checkValue)
+OFCondition IODEnhUSImageModule::setAcquisitionDateTime(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDateTime::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_AcquisitionDateTime, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDateTime::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_AcquisitionDateTime, value);
+    return result;
 }
 
-
-OFCondition IODEnhUSImageModule::setAcquisitionDuration(const Float64 value,
-                                                        const OFBool)
+OFCondition IODEnhUSImageModule::setAcquisitionDuration(const Float64 value, const OFBool)
 {
-  return m_Item->putAndInsertFloat64(DCM_AcquisitionDuration, value);
+    return m_Item->putAndInsertFloat64(DCM_AcquisitionDuration, value);
 }
 
-
-OFCondition IODEnhUSImageModule::setPixelSpacing(const OFString& value,
-                                                 const OFBool checkValue)
+OFCondition IODEnhUSImageModule::setPixelSpacing(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "2") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_PixelSpacing, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "2") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_PixelSpacing, value);
+    return result;
 }
 
-
-OFCondition IODEnhUSImageModule::setPositionMeasuringDevice(const OFString& value,
-                                                            const OFBool checkValue)
+OFCondition IODEnhUSImageModule::setPositionMeasuringDevice(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result;
-  if (checkValue)
-  {
-    result = DcmCodeString::checkStringValue(value, "1");
-    if (result.good())
+    OFCondition result;
+    if (checkValue)
     {
-      if ( (value != "RIGID") && (value != "FREEHAND") )
-        result = IOD_EC_InvalidElementValue;
+        result = DcmCodeString::checkStringValue(value, "1");
+        if (result.good())
+        {
+            if ((value != "RIGID") && (value != "FREEHAND"))
+                result = IOD_EC_InvalidElementValue;
+        }
     }
-  }
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_PositionMeasuringDeviceUsed, value);
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_PositionMeasuringDeviceUsed, value);
 
-  return result;
+    return result;
 }
 
-
-OFCondition IODEnhUSImageModule::setLossyImageCompression(const OFString& value,
-                                                          const OFBool checkValue)
+OFCondition IODEnhUSImageModule::setLossyImageCompression(const OFString& value, const OFBool checkValue)
 {
-  if (checkValue)
-  {
-    if ( (value != "00") && (value != "01") )
-      return IOD_EC_InvalidElementValue;
-  }
+    if (checkValue)
+    {
+        if ((value != "00") && (value != "01"))
+            return IOD_EC_InvalidElementValue;
+    }
 
-  return m_Item->putAndInsertOFStringArray(DCM_LossyImageCompression, value);
+    return m_Item->putAndInsertOFStringArray(DCM_LossyImageCompression, value);
 }
 
-
-
-OFCondition IODEnhUSImageModule::setLossyImageCompressionMethod(const OFString& value,
-                                                                const OFBool checkValue)
+OFCondition IODEnhUSImageModule::setLossyImageCompressionMethod(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1-n") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_LossyImageCompressionMethod, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1-n") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_LossyImageCompressionMethod, value);
+    return result;
 }
 
-
-OFCondition IODEnhUSImageModule::setLossyImageCompressionRatio(const OFString& value,
-                                                               const OFBool checkValue)
+OFCondition IODEnhUSImageModule::setLossyImageCompressionRatio(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1-n") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_LossyImageCompressionRatio, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1-n") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_LossyImageCompressionRatio, value);
+    return result;
 }
 
-
-OFCondition IODEnhUSImageModule::setRecognizableVisibleFeatures(const OFString& value,
-                                                                const OFBool checkValue)
+OFCondition IODEnhUSImageModule::setRecognizableVisibleFeatures(const OFString& value, const OFBool checkValue)
 {
-  if (checkValue)
-  {
-    if ( (value != "NO" ) && (value != "YES") )
-      return IOD_EC_InvalidElementValue;
-  }
-  return m_Item->putAndInsertOFStringArray(DCM_RecognizableVisualFeatures, value);
+    if (checkValue)
+    {
+        if ((value != "NO") && (value != "YES"))
+            return IOD_EC_InvalidElementValue;
+    }
+    return m_Item->putAndInsertOFStringArray(DCM_RecognizableVisualFeatures, value);
 }
 
-
-OFCondition IODEnhUSImageModule::setProcessingFunction(const OFString& value,
-                                                       const OFBool checkValue)
+OFCondition IODEnhUSImageModule::setProcessingFunction(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_ProcessingFunction, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_ProcessingFunction, value);
+    return result;
 }
 
-
-OFCondition IODEnhUSImageModule::setMechanicalIndex(const OFString& value,
-                                                    const OFBool checkValue)
+OFCondition IODEnhUSImageModule::setMechanicalIndex(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_MechanicalIndex, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_MechanicalIndex, value);
+    return result;
 }
 
-
-OFCondition IODEnhUSImageModule::setBoneThermalIndex(const OFString& value,
-                                                     const OFBool checkValue)
+OFCondition IODEnhUSImageModule::setBoneThermalIndex(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_BoneThermalIndex, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_BoneThermalIndex, value);
+    return result;
 }
 
-
-OFCondition IODEnhUSImageModule::setCranialThermalIndex(const OFString& value,
-                                                        const bool checkValue)
+OFCondition IODEnhUSImageModule::setCranialThermalIndex(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_CranialThermalIndex, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_CranialThermalIndex, value);
+    return result;
 }
 
-
-OFCondition IODEnhUSImageModule::setSoftTissueThermalIndex(const OFString& value,
-                                                           const bool checkValue)
+OFCondition IODEnhUSImageModule::setSoftTissueThermalIndex(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_SoftTissueThermalIndex, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_SoftTissueThermalIndex, value);
+    return result;
 }
 
-
-OFCondition IODEnhUSImageModule::setDepthsOfFocus(const Float64 value,
-                                                  const long unsigned int pos,
-                                                  const bool checkValue)
+OFCondition
+IODEnhUSImageModule::setDepthsOfFocus(const Float64 value, const long unsigned int pos, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertFloat64(DCM_DepthsOfFocus, value, pos);
+    (void)checkValue;
+    return m_Item->putAndInsertFloat64(DCM_DepthsOfFocus, value, pos);
 }
 
-
-OFCondition IODEnhUSImageModule::setDepthsOfFocus(const OFVector< Float64 >& values,
-                                                  const bool checkValue)
+OFCondition IODEnhUSImageModule::setDepthsOfFocus(const OFVector<Float64>& values, const OFBool checkValue)
 {
-  (void)checkValue;
-  DcmElement* elem = DcmItem::newDicomElement(DCM_DepthsOfFocus);
-  if (!elem)
-    return EC_MemoryExhausted;
+    (void)checkValue;
+    DcmElement* elem = DcmItem::newDicomElement(DCM_DepthsOfFocus);
+    if (!elem)
+        return EC_MemoryExhausted;
 
-  OFCondition result;
-  OFVector<Float64>::const_iterator it = values.begin();
-  while ((it != values.end()) && result.good())
-  {
-    result = elem->putFloat64(*it);
-    it++;
-  }
-  if (result.bad())
-  {
-    delete elem;
-  }
-  else
-  {
-    result = m_Item->insert(elem);
-  }
-  return result;
+    OFCondition result;
+    OFVector<Float64>::const_iterator it = values.begin();
+    while ((it != values.end()) && result.good())
+    {
+        result = elem->putFloat64(*it);
+        it++;
+    }
+    if (result.bad())
+    {
+        delete elem;
+    }
+    else
+    {
+        result = m_Item->insert(elem);
+    }
+    return result;
 }
 
-
-OFCondition IODEnhUSImageModule::setDepthsOfScanField(const OFString& value,
-                                                      const bool checkValue)
+OFCondition IODEnhUSImageModule::setDepthsOfScanField(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmIntegerString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_DepthOfScanField, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmIntegerString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_DepthOfScanField, value);
+    return result;
 }
index 932bf4403b838fa42ed07547c577f5c652cdf056..eba838777b0229ad0d2ceed5fec31c82bdcdf282 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modenhusseries.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/iodutil.h"
 
 const OFString IODEnhancedUSSeriesModule::m_ModuleName = "EnhancedUSSeries";
 
-
-IODEnhancedUSSeriesModule::IODEnhancedUSSeriesModule(OFshared_ptr<DcmItem> item,
-                                                     OFshared_ptr<IODRules> rules)
-: IODModule(item, rules),
-  m_ReferencedPerformedProcedureStep(),
-  m_PerformedProtocolCode()
+IODEnhancedUSSeriesModule::IODEnhancedUSSeriesModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODModule(item, rules)
+    , m_ReferencedPerformedProcedureStep()
+    , m_PerformedProtocolCode()
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODEnhancedUSSeriesModule::IODEnhancedUSSeriesModule()
-: IODModule(),
-  m_ReferencedPerformedProcedureStep(),
-  m_PerformedProtocolCode()
+    : IODModule()
+    , m_ReferencedPerformedProcedureStep()
+    , m_PerformedProtocolCode()
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 OFString IODEnhancedUSSeriesModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 void IODEnhancedUSSeriesModule::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_Modality, "1","1", getName(), DcmIODTypes::IE_SERIES, "US"), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ReferencedPerformedProcedureStepSequence, "1","1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PerformedProtocolCodeSequence, "1","1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_Modality, "1", "1", getName(), DcmIODTypes::IE_SERIES, "US"), OFTrue);
+    m_Rules->addRule(
+        new IODRule(DCM_ReferencedPerformedProcedureStepSequence, "1", "1C", getName(), DcmIODTypes::IE_SERIES),
+        OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PerformedProtocolCodeSequence, "1", "1C", getName(), DcmIODTypes::IE_SERIES),
+                     OFTrue);
 }
 
-
-OFCondition IODEnhancedUSSeriesModule::read(DcmItem& source,
-                                            const OFBool clearOldData)
+OFCondition IODEnhancedUSSeriesModule::read(DcmItem& source, const OFBool clearOldData)
 {
-  if (clearOldData)
-    clearData();
-
-  IODComponent::read(source, OFFalse /* data already cleared */);
-
-  DcmIODUtil::readSingleItem<SOPInstanceReferenceMacro>(source, DCM_ReferencedPerformedProcedureStepSequence, m_ReferencedPerformedProcedureStep, m_Rules->getByTag(DCM_ReferencedPerformedProcedureStepSequence));
-  DcmIODUtil::readSingleItem<CodeSequenceMacro>(source, DCM_PerformedProtocolCodeSequence, m_PerformedProtocolCode, m_Rules->getByTag(DCM_PerformedProtocolCodeSequence));
-
-  return EC_Normal;
+    if (clearOldData)
+        clearData();
+
+    IODComponent::read(source, OFFalse /* data already cleared */);
+
+    DcmIODUtil::readSingleItem<SOPInstanceReferenceMacro>(
+        source,
+        DCM_ReferencedPerformedProcedureStepSequence,
+        m_ReferencedPerformedProcedureStep,
+        m_Rules->getByTag(DCM_ReferencedPerformedProcedureStepSequence));
+    DcmIODUtil::readSingleItem<CodeSequenceMacro>(source,
+                                                  DCM_PerformedProtocolCodeSequence,
+                                                  m_PerformedProtocolCode,
+                                                  m_Rules->getByTag(DCM_PerformedProtocolCodeSequence));
+
+    return EC_Normal;
 }
 
-
 OFCondition IODEnhancedUSSeriesModule::write(DcmItem& destination)
 {
-  OFCondition result = EC_Normal;
-
-  result = IODComponent::write(destination);
-  DcmIODUtil::writeSingleItem<SOPInstanceReferenceMacro>(result, DCM_ReferencedPerformedProcedureStepSequence, m_ReferencedPerformedProcedureStep, destination, m_Rules->getByTag(DCM_ReferencedPerformedProcedureStepSequence));
-  DcmIODUtil::writeSingleItem<CodeSequenceMacro>(result, DCM_PerformedProtocolCodeSequence, m_PerformedProtocolCode, destination, m_Rules->getByTag(DCM_PerformedProtocolCodeSequence));
-
-  return result;
+    OFCondition result = EC_Normal;
+
+    result = IODComponent::write(destination);
+    DcmIODUtil::writeSingleItem<SOPInstanceReferenceMacro>(
+        result,
+        DCM_ReferencedPerformedProcedureStepSequence,
+        m_ReferencedPerformedProcedureStep,
+        destination,
+        m_Rules->getByTag(DCM_ReferencedPerformedProcedureStepSequence));
+    DcmIODUtil::writeSingleItem<CodeSequenceMacro>(result,
+                                                   DCM_PerformedProtocolCodeSequence,
+                                                   m_PerformedProtocolCode,
+                                                   destination,
+                                                   m_Rules->getByTag(DCM_PerformedProtocolCodeSequence));
+
+    return result;
 }
 
-
 IODEnhancedUSSeriesModule::~IODEnhancedUSSeriesModule()
 {
 }
 
-
-OFCondition IODEnhancedUSSeriesModule::getModality(OFString &value,
-                                                   const signed long pos) const
+OFCondition IODEnhancedUSSeriesModule::getModality(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_Modality, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_Modality, *m_Item, value, pos);
 }
 
-
 CodeSequenceMacro& IODEnhancedUSSeriesModule::getPerformedProtocolCode()
 {
-  return m_PerformedProtocolCode;
+    return m_PerformedProtocolCode;
 }
 
-
 SOPInstanceReferenceMacro& IODEnhancedUSSeriesModule::getReferencedPPS()
 {
-  return m_ReferencedPerformedProcedureStep;
+    return m_ReferencedPerformedProcedureStep;
 }
 
-
-OFCondition IODEnhancedUSSeriesModule::getPerformedProtocolType(OFString &value,
-                                                                const signed long pos) const
+OFCondition IODEnhancedUSSeriesModule::getPerformedProtocolType(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_PerformedProtocolType, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_PerformedProtocolType, *m_Item, value, pos);
 }
index eadd5275d6bd1ea3d0d98f85698efbe364d7ae68..c45d2cffdf567ef843c03f748b9be0dc0338e087 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modequipment.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmdata/dcdeftag.h"
 #include "dcmtk/dcmdata/dcvrlo.h"
-#include "dcmtk/dcmdata/dcvrst.h"
 #include "dcmtk/dcmdata/dcvrsh.h"
+#include "dcmtk/dcmdata/dcvrst.h"
 #include "dcmtk/dcmiod/iodutil.h"
 
-IODGeneralEquipmentModule::IODGeneralEquipmentModule(OFshared_ptr<DcmItem> item,
-                                                     OFshared_ptr<IODRules> rules)
-: IODModule(item, rules),
-  m_ModuleName("GeneralEquipmentModule")
+IODGeneralEquipmentModule::IODGeneralEquipmentModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODModule(item, rules)
+    , m_ModuleName("GeneralEquipmentModule")
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODGeneralEquipmentModule::IODGeneralEquipmentModule()
-: IODModule(),
-  m_ModuleName("GeneralEquipmentModule")
+    : IODModule()
+    , m_ModuleName("GeneralEquipmentModule")
 {
-  resetRules();
+    resetRules();
 }
 
-
 void IODGeneralEquipmentModule::resetRules()
 {
 
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_Manufacturer, "1", "2", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_InstitutionName, "1", "3", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_InstitutionAddress, "1", "3", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_StationName, "1", "3", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_InstitutionalDepartmentName, "1", "3", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ManufacturerModelName, "1", "3", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_DeviceSerialNumber, "1", "3", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_SoftwareVersions, "1-n", "3", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_Manufacturer, "1", "2", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_InstitutionName, "1", "3", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_InstitutionAddress, "1", "3", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_StationName, "1", "3", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_InstitutionalDepartmentName, "1", "3", getName(), DcmIODTypes::IE_EQUIPMENT),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ManufacturerModelName, "1", "3", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_DeviceSerialNumber, "1", "3", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_SoftwareVersions, "1-n", "3", getName(), DcmIODTypes::IE_EQUIPMENT), OFTrue);
 }
 
-
 IODGeneralEquipmentModule::~IODGeneralEquipmentModule()
 {
 }
 
-
 OFString IODGeneralEquipmentModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
-OFCondition IODGeneralEquipmentModule::getDeviceSerialNumber(OFString& value,
-                                                             const long signed int pos) const
+OFCondition IODGeneralEquipmentModule::getDeviceSerialNumber(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_DeviceSerialNumber, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_DeviceSerialNumber, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralEquipmentModule::getManufacturer(OFString& value,
-                                                       const long signed int pos) const
+OFCondition IODGeneralEquipmentModule::getManufacturer(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_Manufacturer, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_Manufacturer, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralEquipmentModule::getInstitutionName(OFString& value,
-                                                          const long signed int pos) const
+OFCondition IODGeneralEquipmentModule::getInstitutionName(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_InstitutionName, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_InstitutionName, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralEquipmentModule::getInstitutionAddress(OFString& value,
-                                                             const long signed int pos) const
+OFCondition IODGeneralEquipmentModule::getInstitutionAddress(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_InstitutionAddress, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_InstitutionAddress, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralEquipmentModule::getStationName(OFString& value,
-                                                      const long signed int pos) const
+OFCondition IODGeneralEquipmentModule::getStationName(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_StationName, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_StationName, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralEquipmentModule::getInstitutionalDepartmentName(OFString& value,
-                                                                      const long signed int pos) const
+OFCondition IODGeneralEquipmentModule::getInstitutionalDepartmentName(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_StationName, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_StationName, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralEquipmentModule::getManufacturerModelName(OFString& value,
-                                                                const long signed int pos) const
+OFCondition IODGeneralEquipmentModule::getManufacturerModelName(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_ManufacturerModelName, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_ManufacturerModelName, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralEquipmentModule::getSoftwareVersions(OFString& value,
-                                                           const long signed int pos) const
+OFCondition IODGeneralEquipmentModule::getSoftwareVersions(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_SoftwareVersions, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_SoftwareVersions, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralEquipmentModule::setDeviceSerialNumber(const OFString& value,
-                                                             const OFBool checkValue)
+OFCondition IODGeneralEquipmentModule::setDeviceSerialNumber(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_DeviceSerialNumber, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_DeviceSerialNumber, value);
+    return result;
 }
 
-
-OFCondition IODGeneralEquipmentModule::setManufacturer(const OFString& value,
-                                                       const OFBool checkValue)
+OFCondition IODGeneralEquipmentModule::setManufacturer(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_Manufacturer, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_Manufacturer, value);
+    return result;
 }
 
-
-OFCondition IODGeneralEquipmentModule::setInstitutionName(const OFString& value,
-                                                          const OFBool checkValue)
+OFCondition IODGeneralEquipmentModule::setInstitutionName(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_InstitutionName, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_InstitutionName, value);
+    return result;
 }
 
-
-OFCondition IODGeneralEquipmentModule::setInstitutionAddress(const OFString& value,
-                                                             const OFBool checkValue)
+OFCondition IODGeneralEquipmentModule::setInstitutionAddress(const OFString& value, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertOFStringArray(DCM_InstitutionAddress, value);
+    (void)checkValue;
+    return m_Item->putAndInsertOFStringArray(DCM_InstitutionAddress, value);
 }
 
-
-OFCondition IODGeneralEquipmentModule::setStationName(const OFString& value,
-                                                      const OFBool checkValue)
+OFCondition IODGeneralEquipmentModule::setStationName(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_StationName, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_StationName, value);
+    return result;
 }
 
-
-OFCondition IODGeneralEquipmentModule::setInstutionalDepartmentName(const OFString& value,
-                                                                    const OFBool checkValue)
+OFCondition IODGeneralEquipmentModule::setInstutionalDepartmentName(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_InstitutionalDepartmentName, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_InstitutionalDepartmentName, value);
+    return result;
 }
 
-
-OFCondition IODGeneralEquipmentModule::setManufacturerModelName(const OFString& value,
-                                                                const OFBool checkValue)
+OFCondition IODGeneralEquipmentModule::setManufacturerModelName(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_ManufacturerModelName, value);
-  return result;
-
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_ManufacturerModelName, value);
+    return result;
 }
 
-
-OFCondition IODGeneralEquipmentModule::setSoftwareVersions(const OFString& value,
-                                                           const OFBool checkValue)
+OFCondition IODGeneralEquipmentModule::setSoftwareVersions(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1-n") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_SoftwareVersions, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1-n") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_SoftwareVersions, value);
+    return result;
 }
index d5e1494ec5984bb0db8609f76233f57963f5e03f..979a497395ba98d29ac0b2ead315ee77f1491ebe 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modfloatingpointimagepixel.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmdata/dcdeftag.h"
-#include "dcmtk/dcmdata/dcvrfl.h"
 #include "dcmtk/dcmdata/dcvrfd.h"
+#include "dcmtk/dcmdata/dcvrfl.h"
 #include "dcmtk/dcmiod/iodutil.h"
 
-const OFString IODFloatingPointImagePixelModule::m_ModuleName = "FloatingPointImagePixelModule";
-const DcmTagKey IODFloatingPointImagePixelModule::pixel_data_tag = DCM_FloatPixelData;
+const OFString IODFloatingPointImagePixelModule::m_ModuleName          = "FloatingPointImagePixelModule";
+const DcmTagKey IODFloatingPointImagePixelModule::pixel_data_tag       = DCM_FloatPixelData;
 const DcmTagKey IODDoubleFloatingPointImagePixelModule::pixel_data_tag = DCM_DoubleFloatPixelData;
 
-
 IODFloatingPointImagePixelModule::IODFloatingPointImagePixelModule(OFshared_ptr<DcmItem> item,
                                                                    OFshared_ptr<IODRules> rules)
-: IODImagePixelBase(item, rules)
+    : IODImagePixelBase(item, rules)
 {
-  // reset element rules
-  resetRules();
-  getData().putAndInsertUint16(DCM_BitsAllocated, 32);
-  getData().putAndInsertUint16(DCM_SamplesPerPixel, 1);
-  getData().putAndInsertUint16(DCM_PixelRepresentation, 1);
-  getData().putAndInsertOFStringArray(DCM_PhotometricInterpretation, "MONOCHROME2");
+    // reset element rules
+    resetRules();
+    getData().putAndInsertUint16(DCM_BitsAllocated, 32);
+    getData().putAndInsertUint16(DCM_SamplesPerPixel, 1);
+    getData().putAndInsertUint16(DCM_PixelRepresentation, 1);
+    getData().putAndInsertOFStringArray(DCM_PhotometricInterpretation, "MONOCHROME2");
 }
 
-
 OFString IODFloatingPointImagePixelModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 IODFloatingPointImagePixelModule::IODFloatingPointImagePixelModule()
-: IODImagePixelBase()
+    : IODImagePixelBase()
 {
-  resetRules();
+    resetRules();
 }
 
-
 IODFloatingPointImagePixelModule::~IODFloatingPointImagePixelModule()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
 void IODFloatingPointImagePixelModule::resetRules()
 {
-  // Parameters this module is responsible for.
-  m_Rules->addRule(new IODRule(DCM_SamplesPerPixel, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PhotometricInterpretation, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_Rows, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_Columns, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_BitsAllocated, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PixelAspectRatio, "2", "1C", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_FloatPixelPaddingValue, "1", "3", m_ModuleName, DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_FloatPixelPaddingRangeLimit, "1", "1C", m_ModuleName, DcmIODTypes::IE_IMAGE), OFTrue);
+    // Parameters this module is responsible for.
+    m_Rules->addRule(new IODRule(DCM_SamplesPerPixel, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PhotometricInterpretation, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_Rows, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_Columns, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_BitsAllocated, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PixelAspectRatio, "2", "1C", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_FloatPixelPaddingValue, "1", "3", m_ModuleName, DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_FloatPixelPaddingRangeLimit, "1", "1C", m_ModuleName, DcmIODTypes::IE_IMAGE),
+                     OFTrue);
 }
 
-
-OFCondition IODFloatingPointImagePixelModule::read(DcmItem& source,
-                                                  const OFBool clearOldData)
+OFCondition IODFloatingPointImagePixelModule::read(DcmItem& source, const OFBool clearOldData)
 {
-  // Read common attributes
-  IODImagePixelBase::read(source, clearOldData);
-  // Read extra attributes of Floating Point Image Pixel Module
-  IODModule::read(source, clearOldData);
-  return EC_Normal;
+    // Read common attributes
+    IODImagePixelBase::read(source, clearOldData);
+    // Read extra attributes of Floating Point Image Pixel Module
+    IODModule::read(source, clearOldData);
+    return EC_Normal;
 }
 
-
 OFCondition IODFloatingPointImagePixelModule::write(DcmItem& destination)
 {
-  // Write Photometric Interpretation fixed value for Floating Point Image Pixel Module
-  OFCondition result = m_Item->putAndInsertOFStringArray(DCM_PhotometricInterpretation, "MONOCHROME2");
-  // Write common attributes
-  if (result.good())
-  {
-    result = IODImagePixelBase::write(destination);
-  }
-  // Write extra attributes of Floating Poing Image Pixel Module
-  if (result.good())
-  {
-    result = IODModule::write(destination);
-  }
-  return result;
+    // Write Photometric Interpretation fixed value for Floating Point Image Pixel Module
+    OFCondition result = m_Item->putAndInsertOFStringArray(DCM_PhotometricInterpretation, "MONOCHROME2");
+    // Write common attributes
+    if (result.good())
+    {
+        result = IODImagePixelBase::write(destination);
+    }
+    // Write extra attributes of Floating Poing Image Pixel Module
+    if (result.good())
+    {
+        result = IODModule::write(destination);
+    }
+    return result;
 }
 
-
 IODImagePixelBase::DataType IODFloatingPointImagePixelModule::getDataType() const
 {
-  return IODImagePixelBase::DATA_TYPE_FLOAT;
+    return IODImagePixelBase::DATA_TYPE_FLOAT;
 }
 
-
-OFCondition IODFloatingPointImagePixelModule::getFloatPixelPaddingValue(Float32& value,
-                                                                        const long pos)
+OFCondition IODFloatingPointImagePixelModule::getFloatPixelPaddingValue(Float32& value, const unsigned long pos)
 {
-  return m_Item->findAndGetFloat32(DCM_FloatPixelPaddingValue, value, pos);
+    return m_Item->findAndGetFloat32(DCM_FloatPixelPaddingValue, value, pos);
 }
 
-
-OFCondition IODFloatingPointImagePixelModule::getFloatPixelPaddingRangeLimit(Float32& value,
-                                                                             const long pos)
+OFCondition IODFloatingPointImagePixelModule::getFloatPixelPaddingRangeLimit(Float32& value, const unsigned long pos)
 {
-  return m_Item->findAndGetFloat32(DCM_FloatPixelPaddingRangeLimit, value, pos);
+    return m_Item->findAndGetFloat32(DCM_FloatPixelPaddingRangeLimit, value, pos);
 }
 
-
-OFCondition IODFloatingPointImagePixelModule::setFloatPixelPaddingValue(const Float32 value,
-                                                                        const OFBool checkValue)
+OFCondition IODFloatingPointImagePixelModule::setFloatPixelPaddingValue(const Float32 value, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertFloat32(DCM_FloatPixelPaddingValue, value);
+    (void)checkValue;
+    return m_Item->putAndInsertFloat32(DCM_FloatPixelPaddingValue, value);
 }
 
-
 OFCondition IODFloatingPointImagePixelModule::setFloatPixelPaddingRangeLimit(const Float32 value,
                                                                              const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertFloat32(DCM_FloatPixelPaddingRangeLimit, value);
+    (void)checkValue;
+    return m_Item->putAndInsertFloat32(DCM_FloatPixelPaddingRangeLimit, value);
 }
 
 // ---------------- Double Floating Point Image Pixel Module ------------------
 
 const OFString IODDoubleFloatingPointImagePixelModule::m_ModuleName = "DoubleFloatingPointImagePixelModule";
 
-
 IODDoubleFloatingPointImagePixelModule::IODDoubleFloatingPointImagePixelModule(OFshared_ptr<DcmItem> item,
                                                                                OFshared_ptr<IODRules> rules)
-: IODImagePixelBase(item, rules)
+    : IODImagePixelBase(item, rules)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 
-  getData().putAndInsertUint16(DCM_BitsAllocated, 64);
-  getData().putAndInsertUint16(DCM_SamplesPerPixel, 1);
-  getData().putAndInsertUint16(DCM_PixelRepresentation, 1);
-  getData().putAndInsertOFStringArray(DCM_PhotometricInterpretation, "MONOCHROME2");
+    getData().putAndInsertUint16(DCM_BitsAllocated, 64);
+    getData().putAndInsertUint16(DCM_SamplesPerPixel, 1);
+    getData().putAndInsertUint16(DCM_PixelRepresentation, 1);
+    getData().putAndInsertOFStringArray(DCM_PhotometricInterpretation, "MONOCHROME2");
 }
 
-
 OFString IODDoubleFloatingPointImagePixelModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 IODDoubleFloatingPointImagePixelModule::IODDoubleFloatingPointImagePixelModule()
-: IODImagePixelBase()
+    : IODImagePixelBase()
 {
-  resetRules();
+    resetRules();
 }
 
-
 IODDoubleFloatingPointImagePixelModule::~IODDoubleFloatingPointImagePixelModule()
 {
-  // nothing to do
+    // nothing to do
 }
 
-
 void IODDoubleFloatingPointImagePixelModule::resetRules()
 {
-  // Parameters are tag, VM, type. Overwrite old rules if any.
-  // Take over responsibility for Photometric Interpretation since we want to write
-  // "MONOCHROME2" as a fixed value.
-  m_Rules->addRule(new IODRule(DCM_SamplesPerPixel, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PhotometricInterpretation, "1", "1", getName(), DcmIODTypes::IE_IMAGE, "MONOCHROME2"), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_Rows, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_Columns, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_BitsAllocated, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PixelAspectRatio, "2", "1C", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_DoubleFloatPixelPaddingValue, "1", "3", m_ModuleName, DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_DoubleFloatPixelPaddingRangeLimit, "1", "1C", m_ModuleName, DcmIODTypes::IE_IMAGE), OFTrue);
+    // Parameters are tag, VM, type. Overwrite old rules if any.
+    // Take over responsibility for Photometric Interpretation since we want to write
+    // "MONOCHROME2" as a fixed value.
+    m_Rules->addRule(new IODRule(DCM_SamplesPerPixel, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(
+        new IODRule(DCM_PhotometricInterpretation, "1", "1", getName(), DcmIODTypes::IE_IMAGE, "MONOCHROME2"), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_Rows, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_Columns, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_BitsAllocated, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PixelAspectRatio, "2", "1C", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_DoubleFloatPixelPaddingValue, "1", "3", m_ModuleName, DcmIODTypes::IE_IMAGE),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_DoubleFloatPixelPaddingRangeLimit, "1", "1C", m_ModuleName, DcmIODTypes::IE_IMAGE),
+                     OFTrue);
 }
 
-
-OFCondition IODDoubleFloatingPointImagePixelModule::read(DcmItem& source,
-                                                         const OFBool clearOldData)
+OFCondition IODDoubleFloatingPointImagePixelModule::read(DcmItem& source, const OFBool clearOldData)
 {
-  // Read common attributes
-  IODImagePixelBase::read(source, clearOldData);
-  // Read extra attributes of Floating Point Image Pixel Module
-  IODModule::read(source, clearOldData);
-  return EC_Normal;
+    // Read common attributes
+    IODImagePixelBase::read(source, clearOldData);
+    // Read extra attributes of Floating Point Image Pixel Module
+    IODModule::read(source, clearOldData);
+    return EC_Normal;
 }
 
-
 OFCondition IODDoubleFloatingPointImagePixelModule::write(DcmItem& destination)
 {
-  // Write Photometric Interpretation fixed value for Floating Point Image Pixel Module
-  OFCondition result = m_Item->putAndInsertOFStringArray(DCM_PhotometricInterpretation, "MONOCHROME2");
-  // Write common attributes
-  if (result.good())
-  {
-    result = IODImagePixelBase::write(destination);
-  }
-  // Write extra attributes of Floating Poing Image Pixel Module
-  if (result.good())
-  {
-    result = IODModule::write(destination);
-  }
-  return result;
+    // Write Photometric Interpretation fixed value for Floating Point Image Pixel Module
+    OFCondition result = m_Item->putAndInsertOFStringArray(DCM_PhotometricInterpretation, "MONOCHROME2");
+    // Write common attributes
+    if (result.good())
+    {
+        result = IODImagePixelBase::write(destination);
+    }
+    // Write extra attributes of Floating Poing Image Pixel Module
+    if (result.good())
+    {
+        result = IODModule::write(destination);
+    }
+    return result;
 }
 
-
 IODImagePixelBase::DataType IODDoubleFloatingPointImagePixelModule::getDataType() const
 {
-  return IODImagePixelBase::DATA_TYPE_DOUBLE;
+    return IODImagePixelBase::DATA_TYPE_DOUBLE;
 }
 
-
 OFCondition IODDoubleFloatingPointImagePixelModule::getDoubleFloatPixelPaddingValue(Float64& value,
-                                                                                    const long pos)
+                                                                                    const unsigned long pos)
 {
-  return m_Item->findAndGetFloat64(DCM_FloatPixelPaddingValue, value, pos);
+    return m_Item->findAndGetFloat64(DCM_FloatPixelPaddingValue, value, pos);
 }
 
-
 OFCondition IODDoubleFloatingPointImagePixelModule::getDoubleFloatPixelPaddingRangeLimit(Float64& value,
-                                                                                         const long pos)
+                                                                                         const unsigned long pos)
 {
-  return m_Item->findAndGetFloat64(DCM_DoubleFloatPixelPaddingRangeLimit, value, pos);
+    return m_Item->findAndGetFloat64(DCM_DoubleFloatPixelPaddingRangeLimit, value, pos);
 }
 
-
 OFCondition IODDoubleFloatingPointImagePixelModule::setDoubleFloatPixelPaddingValue(const Float64 value,
                                                                                     const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertFloat64(DCM_DoubleFloatPixelPaddingValue, value);
+    (void)checkValue;
+    return m_Item->putAndInsertFloat64(DCM_DoubleFloatPixelPaddingValue, value);
 }
 
-
 OFCondition IODDoubleFloatingPointImagePixelModule::setDoubleFloatPixelPaddingRangeLimit(const Float64 value,
                                                                                          const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertFloat64(DCM_DoubleFloatPixelPaddingRangeLimit, value);
+    (void)checkValue;
+    return m_Item->putAndInsertFloat64(DCM_DoubleFloatPixelPaddingRangeLimit, value);
 }
index 3e331666f368ad262a596259f8b8824d99db4f2b..f664fb0e1691e753a858b1152153655a4b5935b1 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modfor.h"
-#include "dcmtk/dcmdata/dcvrui.h"
-#include "dcmtk/dcmdata/dcvrlo.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmdata/dcvrlo.h"
+#include "dcmtk/dcmdata/dcvrui.h"
 #include "dcmtk/dcmiod/iodutil.h"
 
 const OFString IODFoRModule::m_ModuleName = "FrameOfReferenceModule";
 
-
-IODFoRModule::IODFoRModule(OFshared_ptr<DcmItem> item,
-                           OFshared_ptr<IODRules> rules)
-: IODModule(item, rules)
+IODFoRModule::IODFoRModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODModule(item, rules)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODFoRModule::IODFoRModule()
-: IODModule()
+    : IODModule()
 {
-  resetRules();
+    resetRules();
 }
 
-
 void IODFoRModule::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_FrameOfReferenceUID, "1","1", getName(), DcmIODTypes::IE_FOR), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PositionReferenceIndicator, "1","2", getName(), DcmIODTypes::IE_FOR), OFTrue);
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_FrameOfReferenceUID, "1", "1", getName(), DcmIODTypes::IE_FOR), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PositionReferenceIndicator, "1", "2", getName(), DcmIODTypes::IE_FOR), OFTrue);
 }
 
-
 OFString IODFoRModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 IODFoRModule::~IODFoRModule()
 {
-  // Nothing to do
+    // Nothing to do
 }
 
-
-OFCondition IODFoRModule::getFrameOfReferenceUID(OFString& value,
-                                                 const signed long pos) const
+OFCondition IODFoRModule::getFrameOfReferenceUID(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_FrameOfReferenceUID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_FrameOfReferenceUID, *m_Item, value, pos);
 }
 
-
-OFCondition IODFoRModule::getPositionReferenceIndicator(OFString& value,
-                                                        const signed long pos) const
+OFCondition IODFoRModule::getPositionReferenceIndicator(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_PositionReferenceIndicator, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_PositionReferenceIndicator, *m_Item, value, pos);
 }
 
-
-OFCondition IODFoRModule::setFrameOfReferenceUID(const OFString &value,
-                                                 const OFBool checkValue)
+OFCondition IODFoRModule::setFrameOfReferenceUID(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_FrameOfReferenceUID, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_FrameOfReferenceUID, value);
+    return result;
 }
 
-
-OFCondition IODFoRModule::setPositionReferenceIndicator(const OFString &value,
-                                                        const OFBool checkValue)
+OFCondition IODFoRModule::setPositionReferenceIndicator(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_PositionReferenceIndicator, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_PositionReferenceIndicator, value);
+    return result;
 }
 
-
 void IODFoRModule::ensureFrameOfReferenceUID(const OFBool correctInvalid)
 {
-  OFString uidstr;
+    OFString uidstr;
 
-  // Create new Frame of Reference instance UID if required
-  if (getFrameOfReferenceUID(uidstr).bad() || uidstr.empty() )
-  {
-    setFrameOfReferenceUID(DcmIODUtil::createUID(1 /* Series Level */));
-  }
-  else if (!uidstr.empty() && correctInvalid)
-  {
-    if (DcmUniqueIdentifier::checkStringValue(uidstr, "1").bad())
+    // Create new Frame of Reference instance UID if required
+    if (getFrameOfReferenceUID(uidstr).bad() || uidstr.empty())
+    {
+        setFrameOfReferenceUID(DcmIODUtil::createUID(1 /* Series Level */));
+    }
+    else if (!uidstr.empty() && correctInvalid)
     {
-      setFrameOfReferenceUID(DcmIODUtil::createUID(1 /* Series Level */));
+        if (DcmUniqueIdentifier::checkStringValue(uidstr, "1").bad())
+        {
+            setFrameOfReferenceUID(DcmIODUtil::createUID(1 /* Series Level */));
+        }
     }
-  }
 }
-
index 3b71561d9933cde565a33a1554c90daf9030245d..247f360785a3d70710d4172448340b50afb6dcb8 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2020, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modgeneralimage.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmdata/dcdeftag.h"
-#include "dcmtk/dcmdata/dcvrui.h"
-#include "dcmtk/dcmdata/dcvrtm.h"
-#include "dcmtk/dcmdata/dcvrdt.h"
 #include "dcmtk/dcmdata/dcvrcs.h"
+#include "dcmtk/dcmdata/dcvrda.h"
 #include "dcmtk/dcmdata/dcvrds.h"
+#include "dcmtk/dcmdata/dcvrdt.h"
 #include "dcmtk/dcmdata/dcvris.h"
-#include "dcmtk/dcmdata/dcvrda.h"
 #include "dcmtk/dcmdata/dcvrlt.h"
-
+#include "dcmtk/dcmdata/dcvrtm.h"
+#include "dcmtk/dcmdata/dcvrui.h"
 
 #include "dcmtk/dcmiod/iodutil.h"
 
 const OFString IODGeneralImageModule::m_ModuleName = "GeneralImageModule";
 
-
-IODGeneralImageModule::IODGeneralImageModule( OFshared_ptr<DcmItem> item,
-                                              OFshared_ptr<IODRules> rules)
-: IODModule(item, rules)
+IODGeneralImageModule::IODGeneralImageModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODModule(item, rules)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODGeneralImageModule::IODGeneralImageModule()
-: IODModule()
+    : IODModule()
 {
-  resetRules();
+    resetRules();
 }
 
-
 IODGeneralImageModule::~IODGeneralImageModule()
 {
 }
 
-
 void IODGeneralImageModule::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_InstanceNumber, "1", "2", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PatientOrientation, "2", "2C", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ContentDate, "1", "2C", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ContentTime, "1", "2C", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ImageType, "2-n", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_AcquisitionNumber, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_AcquisitionDate, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_AcquisitionTime, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_AcquisitionDateTime, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ImageComments, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_BurnedInAnnotation, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_RecognizableVisualFeatures, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_LossyImageCompression, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_LossyImageCompressionRatio, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_LossyImageCompressionMethod, "1-n", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PresentationLUTShape, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_IrradiationEventUID, "1-n", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_InstanceNumber, "1", "2", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PatientOrientation, "2", "2C", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ContentDate, "1", "2C", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ContentTime, "1", "2C", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ImageType, "2-n", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_AcquisitionNumber, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_AcquisitionDate, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_AcquisitionTime, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_AcquisitionDateTime, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ImageComments, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_BurnedInAnnotation, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_RecognizableVisualFeatures, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_LossyImageCompression, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_LossyImageCompressionRatio, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_LossyImageCompressionMethod, "1-n", "3", getName(), DcmIODTypes::IE_IMAGE),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PresentationLUTShape, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_IrradiationEventUID, "1-n", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
 }
 
-
 OFString IODGeneralImageModule::getName() const
 {
-  return "GeneralImageModule";
+    return "GeneralImageModule";
 }
 
-
-
-OFCondition IODGeneralImageModule::getInstanceNumber(OFString &value,
-                                                     const signed long pos)
+OFCondition IODGeneralImageModule::getInstanceNumber(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_InstanceNumber, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_InstanceNumber, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralImageModule::getPatientOrientation(OFString &value,
-                                                         const signed long pos)
+OFCondition IODGeneralImageModule::getPatientOrientation(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_PatientOrientation, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_PatientOrientation, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralImageModule::getContentDate(OFString &value,
-                                                  const signed long pos)
+OFCondition IODGeneralImageModule::getContentDate(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_ContentDate, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_ContentDate, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralImageModule::getContentTime(OFString &value,
-                                                  const signed long pos)
+OFCondition IODGeneralImageModule::getContentTime(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_ContentTime, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_ContentTime, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralImageModule::getImageType(OFString &value,
-                                                const signed long pos)
+OFCondition IODGeneralImageModule::getImageType(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_ImageType, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_ImageType, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralImageModule::getAcquisitionNumber(OFString &value,
-                                                        const signed long pos)
+OFCondition IODGeneralImageModule::getAcquisitionNumber(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_AcquisitionNumber, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_AcquisitionNumber, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralImageModule::getAcquisitionDate(OFString &value,
-                                                      const signed long pos)
+OFCondition IODGeneralImageModule::getAcquisitionDate(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_AcquisitionDate, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_AcquisitionDate, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralImageModule::getAcquisitionTime(OFString &value,
-                                                      const signed long pos)
+OFCondition IODGeneralImageModule::getAcquisitionTime(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_AcquisitionTime, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_AcquisitionTime, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralImageModule::getAcquisitionDateTime(OFString &value,
-                                                          const signed long pos)
+OFCondition IODGeneralImageModule::getAcquisitionDateTime(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_AcquisitionDateTime, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_AcquisitionDateTime, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralImageModule::getImageComments(OFString &value,
-                                                    const signed long pos)
+OFCondition IODGeneralImageModule::getImageComments(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_ImageComments, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_ImageComments, *m_Item, value, pos);
 }
 
-OFCondition IODGeneralImageModule::getBurnedInAnnotation(OFString &value,
-                                                         const signed long pos)
+OFCondition IODGeneralImageModule::getBurnedInAnnotation(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_BurnedInAnnotation, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_BurnedInAnnotation, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralImageModule::getRecognizableVisualFeatures(OFString &value,
-                                                                 const signed long pos)
+OFCondition IODGeneralImageModule::getRecognizableVisualFeatures(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_RecognizableVisualFeatures, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_RecognizableVisualFeatures, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralImageModule::getLossyImageCompression(OFString &value,
-                                                            const signed long pos)
+OFCondition IODGeneralImageModule::getLossyImageCompression(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_LossyImageCompression, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_LossyImageCompression, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralImageModule::getLossyImageCompressionRatio(OFString &value,
-                                                                 const signed long pos)
+OFCondition IODGeneralImageModule::getLossyImageCompressionRatio(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_LossyImageCompressionRatio, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_LossyImageCompressionRatio, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralImageModule::getLossyImageCompressionMethod(OFString &value,
-                                                                  const signed long pos)
+OFCondition IODGeneralImageModule::getLossyImageCompressionMethod(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_LossyImageCompressionMethod, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_LossyImageCompressionMethod, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralImageModule::getPresentationLUTShape(OFString &value,
-                                                           const signed long pos)
+OFCondition IODGeneralImageModule::getPresentationLUTShape(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_PresentationLUTShape, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_PresentationLUTShape, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralImageModule::getIrradiationEventUID(OFString &value,
-                                                          const signed long pos)
+OFCondition IODGeneralImageModule::getIrradiationEventUID(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_IrradiationEventUID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_IrradiationEventUID, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralImageModule::setInstanceNumber(const OFString &value,
-                                                     const OFBool checkValue)
+OFCondition IODGeneralImageModule::setInstanceNumber(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmIntegerString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_InstanceNumber, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmIntegerString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_InstanceNumber, value);
+    return result;
 }
 
-
-OFCondition IODGeneralImageModule::setPatientOrientation(const OFString &value,
-                                                         const OFBool checkValue)
+OFCondition IODGeneralImageModule::setPatientOrientation(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "2") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_PatientOrientation, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "2") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_PatientOrientation, value);
+    return result;
 }
 
-
-OFCondition IODGeneralImageModule::setContentDate(const OFString &value,
-                                                  const OFBool checkValue)
+OFCondition IODGeneralImageModule::setContentDate(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDate::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_ContentDate, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDate::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_ContentDate, value);
+    return result;
 }
 
-
-OFCondition IODGeneralImageModule::setContentTime(const OFString &value,
-                                                  const OFBool checkValue)
+OFCondition IODGeneralImageModule::setContentTime(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmTime::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_ContentTime, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmTime::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_ContentTime, value);
+    return result;
 }
 
-
-OFCondition IODGeneralImageModule::setImageType(const OFString &value,
-                                                const OFBool checkValue)
+OFCondition IODGeneralImageModule::setImageType(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "2-n") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_ImageType, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "2-n") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_ImageType, value);
+    return result;
 }
 
-
-OFCondition IODGeneralImageModule::setAcquisitionNumber(const OFString &value,
-                                                        const OFBool checkValue)
+OFCondition IODGeneralImageModule::setAcquisitionNumber(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmIntegerString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_AcquisitionNumber, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmIntegerString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_AcquisitionNumber, value);
+    return result;
 }
 
-
-OFCondition IODGeneralImageModule::setAcquisitionDate(const OFString &value,
-                                                      const OFBool checkValue)
+OFCondition IODGeneralImageModule::setAcquisitionDate(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDate::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_AcquisitionDate, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDate::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_AcquisitionDate, value);
+    return result;
 }
 
-
-OFCondition IODGeneralImageModule::setAcquisitionTime(const OFString &value,
-                                                      const OFBool checkValue)
+OFCondition IODGeneralImageModule::setAcquisitionTime(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmTime::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_AcquisitionTime, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmTime::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_AcquisitionTime, value);
+    return result;
 }
 
-
-OFCondition IODGeneralImageModule::setAcquisitionDateTime(const OFString &value,
-                                                          const OFBool checkValue)
+OFCondition IODGeneralImageModule::setAcquisitionDateTime(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDateTime::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_AcquisitionDateTime, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDateTime::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_AcquisitionDateTime, value);
+    return result;
 }
 
-
-OFCondition IODGeneralImageModule::setImageComments(const OFString &value,
-                                                    const OFBool checkValue)
+OFCondition IODGeneralImageModule::setImageComments(const OFString& value, const OFBool checkValue)
 {
-  (void)checkValue;
-  return  m_Item->putAndInsertOFStringArray(DCM_ImageComments, value);
+    (void)checkValue;
+    return m_Item->putAndInsertOFStringArray(DCM_ImageComments, value);
 }
 
-
-OFCondition IODGeneralImageModule::setBurnedInAnnotation(const OFString &value,
-                                                         const OFBool checkValue)
+OFCondition IODGeneralImageModule::setBurnedInAnnotation(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_BurnedInAnnotation, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_BurnedInAnnotation, value);
+    return result;
 }
 
-
-
-OFCondition IODGeneralImageModule::setRecognizableVisualFeatures(const OFString &value,
-                                                                 const OFBool checkValue)
+OFCondition IODGeneralImageModule::setRecognizableVisualFeatures(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_RecognizableVisualFeatures, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_RecognizableVisualFeatures, value);
+    return result;
 }
 
-
-
-OFCondition IODGeneralImageModule::setLossyImageCompression(const OFString &value,
-                                                            const OFBool checkValue)
+OFCondition IODGeneralImageModule::setLossyImageCompression(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_LossyImageCompression, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_LossyImageCompression, value);
+    return result;
 }
 
-
-
-OFCondition IODGeneralImageModule::setLossyImageCompressionRatio(const OFString &value,
-                                                                 const OFBool checkValue)
+OFCondition IODGeneralImageModule::setLossyImageCompressionRatio(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_LossyImageCompressionRatio, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1-n") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_LossyImageCompressionRatio, value);
+    return result;
 }
 
-
-OFCondition IODGeneralImageModule::setLossyImageCompressionMethod(const OFString &value,
-                                                                  const OFBool checkValue)
+OFCondition IODGeneralImageModule::setLossyImageCompressionMethod(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1-n") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_LossyImageCompressionMethod, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1-n") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_LossyImageCompressionMethod, value);
+    return result;
 }
 
-
-OFCondition IODGeneralImageModule::setPresentationLUTShape(const OFString &value,
-                                                           const OFBool checkValue)
+OFCondition IODGeneralImageModule::setLossyImageCompressionFlag(const OFString& ratios,
+                                                                const OFString& methods,
+                                                                const OFBool checkValues)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_PresentationLUTShape, value);
-  return result;
+    OFCondition result = setLossyImageCompression("01", checkValues);
+    if (result.good() || !checkValues)
+        result = setLossyImageCompressionMethod(methods, checkValues);
+    if (result.good() || !checkValues)
+        result = setLossyImageCompressionRatio(ratios, checkValues);
+
+    if (checkValues)
+        return result;
+    else
+        return EC_Normal;
 }
 
+OFCondition IODGeneralImageModule::setPresentationLUTShape(const OFString& value, const OFBool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_PresentationLUTShape, value);
+    return result;
+}
 
-OFCondition IODGeneralImageModule::setIrradiationEventUID(const OFString &value,
-                                                          const OFBool checkValue)
+OFCondition IODGeneralImageModule::setIrradiationEventUID(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1-n") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_IrradiationEventUID, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1-n") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_IrradiationEventUID, value);
+    return result;
 }
index 8849fd1976dc9b4ec0517f0b911b7b336d28c14a..aad100ed6af0ac6ab252a064cb293e7ffb1e3c9b 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modgeneralseries.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmdata/dcdeftag.h"
-#include "dcmtk/dcmdata/dcvrui.h"
 #include "dcmtk/dcmdata/dcuid.h"
 #include "dcmtk/dcmdata/dcvrcs.h"
-#include "dcmtk/dcmdata/dcvrlo.h"
 #include "dcmtk/dcmdata/dcvrda.h"
 #include "dcmtk/dcmdata/dcvris.h"
-#include "dcmtk/dcmdata/dcvrtm.h"
+#include "dcmtk/dcmdata/dcvrlo.h"
 #include "dcmtk/dcmdata/dcvrpn.h"
+#include "dcmtk/dcmdata/dcvrtm.h"
+#include "dcmtk/dcmdata/dcvrui.h"
 #include "dcmtk/dcmiod/iodutil.h"
 
 const OFString IODGeneralSeriesModule::m_ModuleName = "GeneralSeriesModule";
 
-
-IODGeneralSeriesModule::IODGeneralSeriesModule(OFshared_ptr<DcmItem> item,
-                                               OFshared_ptr<IODRules> rules)
-: IODModule(item, rules),
-  m_ReferencedPPS()
+IODGeneralSeriesModule::IODGeneralSeriesModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODModule(item, rules)
+    , m_ReferencedPPS()
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODGeneralSeriesModule::IODGeneralSeriesModule()
-: IODModule(),
-  m_ReferencedPPS()
+    : IODModule()
+    , m_ReferencedPPS()
 {
-  resetRules();
+    resetRules();
 }
 
-
 OFString IODGeneralSeriesModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 void IODGeneralSeriesModule::inventMissing()
 {
-  // Series Instance UID
-  ensureInstanceUID();
+    // Series Instance UID
+    ensureInstanceUID();
 
-  // Default handler
-  IODComponent::inventMissing();
+    // Default handler
+    IODComponent::inventMissing();
 }
 
-
 void IODGeneralSeriesModule::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_Modality, "1","1", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_SeriesInstanceUID, "1","1", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_SeriesNumber, "1","2", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_Laterality, "1","2C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_SeriesDate, "1","3", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_SeriesTime, "1","3", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PerformingPhysicianName, "1","3", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ProtocolName, "1","3", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_SeriesDescription, "1","3", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_OperatorsName, "1-n","3", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_BodyPartExamined, "1","3", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PatientPosition, "1","2C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ReferencedPerformedProcedureStepSequence, "1","3", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_Modality, "1", "1", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_SeriesInstanceUID, "1", "1", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_SeriesNumber, "1", "2", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_Laterality, "1", "2C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_SeriesDate, "1", "3", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_SeriesTime, "1", "3", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PerformingPhysicianName, "1", "3", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ProtocolName, "1", "3", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_SeriesDescription, "1", "3", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_OperatorsName, "1-n", "3", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_BodyPartExamined, "1", "3", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PatientPosition, "1", "2C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(
+        new IODRule(DCM_ReferencedPerformedProcedureStepSequence, "1", "3", getName(), DcmIODTypes::IE_SERIES), OFTrue);
 }
 
-
-OFCondition IODGeneralSeriesModule::read(DcmItem& source,
-                                         const OFBool clearOldData)
+OFCondition IODGeneralSeriesModule::read(DcmItem& source, const OFBool clearOldData)
 {
-  if (clearOldData)
-    clearData();
+    if (clearOldData)
+        clearData();
 
-  IODComponent::read(source, OFFalse /* data already cleared */);
-  DcmIODUtil::readSingleItem<SOPInstanceReferenceMacro>(source, DCM_ReferencedPerformedProcedureStepSequence, m_ReferencedPPS, m_Rules->getByTag(DCM_ReferencedPerformedProcedureStepSequence));
+    IODComponent::read(source, OFFalse /* data already cleared */);
+    DcmIODUtil::readSingleItem<SOPInstanceReferenceMacro>(
+        source,
+        DCM_ReferencedPerformedProcedureStepSequence,
+        m_ReferencedPPS,
+        m_Rules->getByTag(DCM_ReferencedPerformedProcedureStepSequence));
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 OFCondition IODGeneralSeriesModule::write(DcmItem& destination)
 {
-  OFCondition result = EC_Normal;
+    OFCondition result = EC_Normal;
 
-  result = IODComponent::write(destination);
-  DcmIODUtil::writeSingleItem<SOPInstanceReferenceMacro>(result, DCM_ReferencedPerformedProcedureStepSequence, m_ReferencedPPS, destination, m_Rules->getByTag(DCM_ReferencedPerformedProcedureStepSequence));
+    result = IODComponent::write(destination);
+    DcmIODUtil::writeSingleItem<SOPInstanceReferenceMacro>(
+        result,
+        DCM_ReferencedPerformedProcedureStepSequence,
+        m_ReferencedPPS,
+        destination,
+        m_Rules->getByTag(DCM_ReferencedPerformedProcedureStepSequence));
 
-  return result;
+    return result;
 }
 
-
 void IODGeneralSeriesModule::ensureInstanceUID(const OFBool correctInvalid)
 {
-  OFString uidstr;
+    OFString uidstr;
 
-  /* create new sop instance UID if required */
-  if (getSeriesInstanceUID(uidstr).bad() || uidstr.empty() )
-  {
-    setSeriesInstanceUID(DcmIODUtil::createUID(1 /* Series Level */));
-  }
-  else if (!uidstr.empty() && correctInvalid)
-  {
-    if (DcmUniqueIdentifier::checkStringValue(uidstr, "1").bad())
+    /* create new sop instance UID if required */
+    if (getSeriesInstanceUID(uidstr).bad() || uidstr.empty())
     {
-      setSeriesInstanceUID(DcmIODUtil::createUID(1 /* Series Level */));    }
-  }
+        setSeriesInstanceUID(DcmIODUtil::createUID(1 /* Series Level */));
+    }
+    else if (!uidstr.empty() && correctInvalid)
+    {
+        if (DcmUniqueIdentifier::checkStringValue(uidstr, "1").bad())
+        {
+            setSeriesInstanceUID(DcmIODUtil::createUID(1 /* Series Level */));
+        }
+    }
 }
 
-
 IODGeneralSeriesModule::~IODGeneralSeriesModule()
 {
 }
 
-
-OFCondition IODGeneralSeriesModule::getModality(OFString &value,
-                                                const signed long pos) const
+OFCondition IODGeneralSeriesModule::getModality(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_Modality, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_Modality, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralSeriesModule::getSeriesInstanceUID(OFString &value,
-                                                         const signed long pos) const
+OFCondition IODGeneralSeriesModule::getSeriesInstanceUID(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_SeriesInstanceUID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_SeriesInstanceUID, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralSeriesModule::getSeriesNumber(OFString &value,
-                                                    const signed long pos) const
+OFCondition IODGeneralSeriesModule::getSeriesNumber(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_SeriesNumber, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_SeriesNumber, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralSeriesModule::getLaterality(OFString& value,
-                                                  const signed long pos) const
+OFCondition IODGeneralSeriesModule::getLaterality(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_Laterality, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_Laterality, *m_Item, value, pos);
 }
 
-
-
-OFCondition IODGeneralSeriesModule::getSeriesDate(OFString &value,
-                                                  const signed long pos) const
+OFCondition IODGeneralSeriesModule::getSeriesDate(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_SeriesDate, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_SeriesDate, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralSeriesModule::getSeriesTime(OFString &value,
-                                                  const signed long pos) const
+OFCondition IODGeneralSeriesModule::getSeriesTime(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_SeriesTime, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_SeriesTime, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralSeriesModule::getPerformingPhysicianName(OFString &value,
-                                                               const signed long pos) const
+OFCondition IODGeneralSeriesModule::getPerformingPhysicianName(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_PerformingPhysicianName, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_PerformingPhysicianName, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralSeriesModule::getProtocolName(OFString &value,
-                                                   const signed long pos) const
+OFCondition IODGeneralSeriesModule::getProtocolName(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_ProtocolName, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_ProtocolName, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralSeriesModule::getSeriesDescription(OFString &value,
-                                                         const signed long pos) const
+OFCondition IODGeneralSeriesModule::getSeriesDescription(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_SeriesDescription, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_SeriesDescription, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralSeriesModule::getOperatorsName(OFString &value,
-                                                    const signed long pos) const
+OFCondition IODGeneralSeriesModule::getOperatorsName(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_OperatorsName, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_OperatorsName, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralSeriesModule::getBodyPartExamined(OFString &value,
-                                                        const signed long pos) const
+OFCondition IODGeneralSeriesModule::getBodyPartExamined(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_BodyPartExamined, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_BodyPartExamined, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralSeriesModule::getPatientPosition(OFString &value,
-                                                       const signed long pos) const
+OFCondition IODGeneralSeriesModule::getPatientPosition(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_PatientPosition, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_PatientPosition, *m_Item, value, pos);
 }
 
-
 SOPInstanceReferenceMacro& IODGeneralSeriesModule::getReferencedPPS()
 {
-  return m_ReferencedPPS;
+    return m_ReferencedPPS;
 }
 
-
-OFCondition IODGeneralSeriesModule::setModality(const OFString &value,
-                                                const OFBool checkValue)
+OFCondition IODGeneralSeriesModule::setModality(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_Modality, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_Modality, value);
+    return result;
 }
 
-
-OFCondition IODGeneralSeriesModule::setSeriesInstanceUID(const OFString &value,
-                                                         const OFBool checkValue)
+OFCondition IODGeneralSeriesModule::setSeriesInstanceUID(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_SeriesInstanceUID, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_SeriesInstanceUID, value);
+    return result;
 }
 
-
-OFCondition IODGeneralSeriesModule::setSeriesNumber(const OFString &value,
-                                                    const OFBool checkValue)
+OFCondition IODGeneralSeriesModule::setSeriesNumber(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmIntegerString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_SeriesNumber, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmIntegerString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_SeriesNumber, value);
+    return result;
 }
 
-
-OFCondition IODGeneralSeriesModule::setLaterality(const DcmIODTypes::IOD_LATERALITY laterality,
-                                                  const OFBool checkValue)
+OFCondition IODGeneralSeriesModule::setLaterality(const DcmIODTypes::IOD_LATERALITY laterality, const OFBool checkValue)
 {
-  (void)checkValue;
-  OFCondition result;
-  switch(laterality)
-  {
-    case DcmIODTypes::LATERALITY_L: result = m_Item->putAndInsertOFStringArray(DCM_Laterality, "L"); break;
-    case DcmIODTypes::LATERALITY_R: result = m_Item->putAndInsertOFStringArray(DCM_Laterality, "R"); break;
-    case DcmIODTypes::LATERALITY_UNDEFINED:
-    default: result = IOD_EC_InvalidLaterality;
-  }
-  return result;
+    (void)checkValue;
+    OFCondition result;
+    switch (laterality)
+    {
+        case DcmIODTypes::LATERALITY_L:
+            result = m_Item->putAndInsertOFStringArray(DCM_Laterality, "L");
+            break;
+        case DcmIODTypes::LATERALITY_R:
+            result = m_Item->putAndInsertOFStringArray(DCM_Laterality, "R");
+            break;
+        case DcmIODTypes::LATERALITY_UNDEFINED:
+        default:
+            result = IOD_EC_InvalidLaterality;
+    }
+    return result;
 }
 
-
-OFCondition IODGeneralSeriesModule::setSeriesDate(const OFString &value,
-                                                  const OFBool checkValue)
+OFCondition IODGeneralSeriesModule::setSeriesDate(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDate::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_SeriesDate, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDate::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_SeriesDate, value);
+    return result;
 }
 
-
-OFCondition IODGeneralSeriesModule::setSeriesTime(const OFString &value,
-                                                  const OFBool checkValue)
+OFCondition IODGeneralSeriesModule::setSeriesTime(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmTime::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_SeriesTime, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmTime::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_SeriesTime, value);
+    return result;
 }
 
-
-OFCondition IODGeneralSeriesModule::setPerformingPhysicianName(const OFString& value,
-                                                               const OFBool checkValue)
+OFCondition IODGeneralSeriesModule::setPerformingPhysicianName(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmPersonName::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_PerformingPhysicianName, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmPersonName::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_PerformingPhysicianName, value);
+    return result;
 }
 
-
-OFCondition IODGeneralSeriesModule::setProtocolName(const OFString& value,
-                                                    const OFBool checkValue)
+OFCondition IODGeneralSeriesModule::setProtocolName(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_ProtocolName, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_ProtocolName, value);
+    return result;
 }
 
-
-OFCondition IODGeneralSeriesModule::setSeriesDescription(const OFString &value,
-                                                         const OFBool checkValue)
+OFCondition IODGeneralSeriesModule::setSeriesDescription(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_SeriesDescription, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_SeriesDescription, value);
+    return result;
 }
 
-
 OFCondition IODGeneralSeriesModule::setOperatorsName(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmPersonName::checkStringValue(value, "1-n") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_OperatorsName, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmPersonName::checkStringValue(value, "1-n") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_OperatorsName, value);
+    return result;
 }
 
-
-OFCondition IODGeneralSeriesModule::setBodyPartExamined(const OFString& value,
-                                                        const OFBool checkValue)
+OFCondition IODGeneralSeriesModule::setBodyPartExamined(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_BodyPartExamined, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_BodyPartExamined, value);
+    return result;
 }
 
-
-OFCondition IODGeneralSeriesModule::setPatientPosition(const OFString& value,
-                                                       const OFBool checkValue)
+OFCondition IODGeneralSeriesModule::setPatientPosition(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_PatientPosition, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_PatientPosition, value);
+    return result;
 }
index e5102b4df595de497e72e534d1f2bde9c2b03f15..ef9d62fa2e0b9d7641111eff181e056826418dc8 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modgeneralstudy.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmdata/dcdeftag.h"
-#include "dcmtk/dcmdata/dcvrui.h"
 #include "dcmtk/dcmdata/dcuid.h"
-#include "dcmtk/dcmdata/dcvrpn.h"
-#include "dcmtk/dcmdata/dcvrlo.h"
 #include "dcmtk/dcmdata/dcvrda.h"
-#include "dcmtk/dcmdata/dcvrtm.h"
+#include "dcmtk/dcmdata/dcvrlo.h"
+#include "dcmtk/dcmdata/dcvrpn.h"
 #include "dcmtk/dcmdata/dcvrsh.h"
+#include "dcmtk/dcmdata/dcvrtm.h"
+#include "dcmtk/dcmdata/dcvrui.h"
 #include "dcmtk/dcmiod/iodutil.h"
 
 const OFString IODGeneralStudyModule::m_ModuleName = "GeneralStudyModule";
 
-
-IODGeneralStudyModule::IODGeneralStudyModule(OFshared_ptr<DcmItem> item,
-                                             OFshared_ptr<IODRules> rules)
-: IODModule(item, rules),
-  m_IssuerOfAccessionNumberSequence(),
-  m_ProcedureCodeSequence(),
-  m_ReasonForPerformedProcedureCodeSequence()
+IODGeneralStudyModule::IODGeneralStudyModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODModule(item, rules)
+    , m_IssuerOfAccessionNumberSequence()
+    , m_ProcedureCodeSequence()
+    , m_ReasonForPerformedProcedureCodeSequence()
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODGeneralStudyModule::IODGeneralStudyModule()
-: IODModule(),
-  m_IssuerOfAccessionNumberSequence(),
-  m_ProcedureCodeSequence(),
-  m_ReasonForPerformedProcedureCodeSequence()
+    : IODModule()
+    , m_IssuerOfAccessionNumberSequence()
+    , m_ProcedureCodeSequence()
+    , m_ReasonForPerformedProcedureCodeSequence()
 {
-  resetRules();
+    resetRules();
 }
 
-
 void IODGeneralStudyModule::inventMissing()
 {
-  // Study Instance UID
-  ensureInstanceUID();
+    // Study Instance UID
+    ensureInstanceUID();
 
-  IODComponent::inventMissing();
+    IODComponent::inventMissing();
 }
 
-
 void IODGeneralStudyModule::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_StudyInstanceUID, "1","1", getName(), DcmIODTypes::IE_STUDY), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_StudyDate, "1","2", getName(), DcmIODTypes::IE_STUDY), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_StudyTime, "1","2", getName(), DcmIODTypes::IE_STUDY), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ReferringPhysicianName, "1","2", getName(), DcmIODTypes::IE_STUDY), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_StudyID, "1","2", getName(), DcmIODTypes::IE_STUDY), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_AccessionNumber, "1","2", getName(), DcmIODTypes::IE_STUDY), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_StudyDescription, "1","3", getName(), DcmIODTypes::IE_STUDY), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_IssuerOfAccessionNumberSequence, "1","3", getName(), DcmIODTypes::IE_STUDY), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ProcedureCodeSequence, "1-n","3", getName(), DcmIODTypes::IE_STUDY), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ReasonForPerformedProcedureCodeSequence, "1-n","3", getName(), DcmIODTypes::IE_STUDY), OFTrue);
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_StudyInstanceUID, "1", "1", getName(), DcmIODTypes::IE_STUDY), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_StudyDate, "1", "2", getName(), DcmIODTypes::IE_STUDY), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_StudyTime, "1", "2", getName(), DcmIODTypes::IE_STUDY), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ReferringPhysicianName, "1", "2", getName(), DcmIODTypes::IE_STUDY), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_StudyID, "1", "2", getName(), DcmIODTypes::IE_STUDY), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_AccessionNumber, "1", "2", getName(), DcmIODTypes::IE_STUDY), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_StudyDescription, "1", "3", getName(), DcmIODTypes::IE_STUDY), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_IssuerOfAccessionNumberSequence, "1", "3", getName(), DcmIODTypes::IE_STUDY),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ProcedureCodeSequence, "1-n", "3", getName(), DcmIODTypes::IE_STUDY), OFTrue);
+    m_Rules->addRule(
+        new IODRule(DCM_ReasonForPerformedProcedureCodeSequence, "1-n", "3", getName(), DcmIODTypes::IE_STUDY), OFTrue);
 }
 
-
 OFString IODGeneralStudyModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 void IODGeneralStudyModule::clearData()
 {
-  m_IssuerOfAccessionNumberSequence.clearData();
-  DcmIODUtil::freeContainer(m_ProcedureCodeSequence);
-  DcmIODUtil::freeContainer(m_ReasonForPerformedProcedureCodeSequence);
+    m_IssuerOfAccessionNumberSequence.clearData();
+    DcmIODUtil::freeContainer(m_ProcedureCodeSequence);
+    DcmIODUtil::freeContainer(m_ReasonForPerformedProcedureCodeSequence);
 }
 
-
-OFCondition IODGeneralStudyModule::read(DcmItem& source,
-                                        const OFBool clearOldData)
+OFCondition IODGeneralStudyModule::read(DcmItem& source, const OFBool clearOldData)
 {
-  if (clearOldData)
-  {
-    clearData();
-  }
+    if (clearOldData)
+    {
+        clearData();
+    }
 
-  IODComponent::read(source, OFFalse /* data already cleared above */);
+    IODComponent::read(source, OFFalse /* data already cleared above */);
 
-  DcmIODUtil::readSingleItem(source, DCM_IssuerOfAccessionNumberSequence, m_IssuerOfAccessionNumberSequence, m_Rules->getByTag(DCM_IssuerOfAccessionNumberSequence));
-  DcmIODUtil::readSubSequence(source, DCM_ProcedureCodeSequence, m_ProcedureCodeSequence, m_Rules->getByTag(DCM_ProcedureCodeSequence));
-  DcmIODUtil::readSubSequence(source, DCM_ReasonForPerformedProcedureCodeSequence, m_ReasonForPerformedProcedureCodeSequence, m_Rules->getByTag(DCM_ReasonForPerformedProcedureCodeSequence));
+    DcmIODUtil::readSingleItem(source,
+                               DCM_IssuerOfAccessionNumberSequence,
+                               m_IssuerOfAccessionNumberSequence,
+                               m_Rules->getByTag(DCM_IssuerOfAccessionNumberSequence));
+    DcmIODUtil::readSubSequence(
+        source, DCM_ProcedureCodeSequence, m_ProcedureCodeSequence, m_Rules->getByTag(DCM_ProcedureCodeSequence));
+    DcmIODUtil::readSubSequence(source,
+                                DCM_ReasonForPerformedProcedureCodeSequence,
+                                m_ReasonForPerformedProcedureCodeSequence,
+                                m_Rules->getByTag(DCM_ReasonForPerformedProcedureCodeSequence));
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 OFCondition IODGeneralStudyModule::write(DcmItem& destination)
 {
-  OFCondition result;
-  DcmIODUtil::writeSingleItem(result, DCM_IssuerOfAccessionNumberSequence, m_IssuerOfAccessionNumberSequence, *m_Item, m_Rules->getByTag(DCM_IssuerOfAccessionNumberSequence));
-  DcmIODUtil::writeSubSequence(result, DCM_ProcedureCodeSequence, m_ProcedureCodeSequence, *m_Item, m_Rules->getByTag(DCM_ProcedureCodeSequence));
-  DcmIODUtil::writeSubSequence(result, DCM_ReasonForPerformedProcedureCodeSequence, m_ReasonForPerformedProcedureCodeSequence, *m_Item, m_Rules->getByTag(DCM_ReasonForPerformedProcedureCodeSequence));
+    OFCondition result;
+    DcmIODUtil::writeSingleItem(result,
+                                DCM_IssuerOfAccessionNumberSequence,
+                                m_IssuerOfAccessionNumberSequence,
+                                *m_Item,
+                                m_Rules->getByTag(DCM_IssuerOfAccessionNumberSequence));
+    DcmIODUtil::writeSubSequence(result,
+                                 DCM_ProcedureCodeSequence,
+                                 m_ProcedureCodeSequence,
+                                 *m_Item,
+                                 m_Rules->getByTag(DCM_ProcedureCodeSequence));
+    DcmIODUtil::writeSubSequence(result,
+                                 DCM_ReasonForPerformedProcedureCodeSequence,
+                                 m_ReasonForPerformedProcedureCodeSequence,
+                                 *m_Item,
+                                 m_Rules->getByTag(DCM_ReasonForPerformedProcedureCodeSequence));
 
-  if (result.good()) result = IODComponent::write(destination);
+    if (result.good())
+        result = IODComponent::write(destination);
 
-  return result;
+    return result;
 }
 
-
-
-
 IODGeneralStudyModule::~IODGeneralStudyModule()
 {
-  DcmIODUtil::freeContainer(m_ProcedureCodeSequence);
-  DcmIODUtil::freeContainer(m_ReasonForPerformedProcedureCodeSequence);
+    DcmIODUtil::freeContainer(m_ProcedureCodeSequence);
+    DcmIODUtil::freeContainer(m_ReasonForPerformedProcedureCodeSequence);
 }
 
-
 void IODGeneralStudyModule::ensureInstanceUID(const OFBool correctInvalid)
 {
-  OFString uidstr;
-
-  /* create new sop instance UID if required */
-  if (getStudyInstanceUID(uidstr).bad() || uidstr.empty() )
-  {
-    setStudyInstanceUID(DcmIODUtil::createUID(2 /* Study Level */));
-  }
-  else if (!uidstr.empty() && correctInvalid)
-  {
-    if (DcmUniqueIdentifier::checkStringValue(uidstr, "1").bad())
+    OFString uidstr;
+
+    /* create new sop instance UID if required */
+    if (getStudyInstanceUID(uidstr).bad() || uidstr.empty())
+    {
+        setStudyInstanceUID(DcmIODUtil::createUID(2 /* Study Level */));
+    }
+    else if (!uidstr.empty() && correctInvalid)
     {
-      setStudyInstanceUID(DcmIODUtil::createUID(2 /* Study Level */));
+        if (DcmUniqueIdentifier::checkStringValue(uidstr, "1").bad())
+        {
+            setStudyInstanceUID(DcmIODUtil::createUID(2 /* Study Level */));
+        }
     }
-  }
 }
 
-
 // --- get attributes (C++ string) ---
 
-OFCondition IODGeneralStudyModule::getStudyInstanceUID(OFString &value,
-                                                       const signed long pos) const
+OFCondition IODGeneralStudyModule::getStudyInstanceUID(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_StudyInstanceUID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_StudyInstanceUID, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralStudyModule::getReferringPhysicianName(OFString &value,
-                                                             const signed long pos) const
+OFCondition IODGeneralStudyModule::getReferringPhysicianName(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_ReferringPhysicianName, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_ReferringPhysicianName, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralStudyModule::getStudyDescription(OFString &value,
-                                                       const signed long pos) const
+OFCondition IODGeneralStudyModule::getStudyDescription(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_StudyDescription, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_StudyDescription, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralStudyModule::getStudyDate(OFString &value,
-                                                const signed long pos) const
+OFCondition IODGeneralStudyModule::getStudyDate(OFString& value, const signed long pos) const
 {
- return DcmIODUtil::getStringValueFromItem(DCM_StudyDate, *m_Item, value, pos);
-
+    return DcmIODUtil::getStringValueFromItem(DCM_StudyDate, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralStudyModule::getStudyTime(OFString &value,
-                                                const signed long pos) const
+OFCondition IODGeneralStudyModule::getStudyTime(OFString& value, const signed long pos) const
 {
- return DcmIODUtil::getStringValueFromItem(DCM_StudyTime, *m_Item, value, pos);
   return DcmIODUtil::getStringValueFromItem(DCM_StudyTime, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralStudyModule::getStudyID(OFString &value,
-                                              const signed long pos) const
+OFCondition IODGeneralStudyModule::getStudyID(OFString& value, const signed long pos) const
 {
- return DcmIODUtil::getStringValueFromItem(DCM_StudyID, *m_Item, value, pos);
   return DcmIODUtil::getStringValueFromItem(DCM_StudyID, *m_Item, value, pos);
 }
 
-
-OFCondition IODGeneralStudyModule::getAccessionNumber(OFString &value,
-                                                      const signed long pos) const
+OFCondition IODGeneralStudyModule::getAccessionNumber(OFString& value, const signed long pos) const
 {
- return DcmIODUtil::getStringValueFromItem(DCM_AccessionNumber, *m_Item, value, pos);
   return DcmIODUtil::getStringValueFromItem(DCM_AccessionNumber, *m_Item, value, pos);
 }
 
-
-HL7HierarchicDesignatorMacro& IODGeneralStudyModule::getIssuerOfAccesionNumber()
+HL7HierarchicDesignatorMacro& IODGeneralStudyModule::getIssuerOfAccessionNumber()
 {
-  return m_IssuerOfAccessionNumberSequence;
+    return m_IssuerOfAccessionNumberSequence;
 }
 
-
-OFVector< CodeSequenceMacro* >& IODGeneralStudyModule::getProcedureCodeSequence()
+OFVector<CodeSequenceMacro*>& IODGeneralStudyModule::getProcedureCodeSequence()
 {
-  return m_ProcedureCodeSequence;
+    return m_ProcedureCodeSequence;
 }
 
-
-OFVector< CodeSequenceMacro* >& IODGeneralStudyModule::getReasonForPerformedProcedureCodeSequence()
+OFVector<CodeSequenceMacro*>& IODGeneralStudyModule::getReasonForPerformedProcedureCodeSequence()
 {
-  return m_ReasonForPerformedProcedureCodeSequence;
+    return m_ReasonForPerformedProcedureCodeSequence;
 }
 
-
 // --- set attributes ---
 
-OFCondition IODGeneralStudyModule::setReferringPhysicianName(const OFString &value,
-                                                             const OFBool checkValue)
+OFCondition IODGeneralStudyModule::setReferringPhysicianName(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmPersonName::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_ReferringPhysicianName,value);
-  return result;
+    OFCondition result = (checkValue) ? DcmPersonName::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_ReferringPhysicianName, value);
+    return result;
 }
 
-
-OFCondition IODGeneralStudyModule::setStudyDescription(const OFString &value,
-                                                       const OFBool checkValue)
+OFCondition IODGeneralStudyModule::setStudyDescription(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result =  m_Item->putAndInsertOFStringArray(DCM_StudyDescription,value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_StudyDescription, value);
+    return result;
 }
 
-
-OFCondition IODGeneralStudyModule::setStudyInstanceUID(const OFString &value,
-                                                       const OFBool checkValue)
+OFCondition IODGeneralStudyModule::setStudyInstanceUID(const OFString& value, const OFBool checkValue)
 {
     OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
     if (result.good())
-      result =  m_Item->putAndInsertOFStringArray(DCM_StudyInstanceUID,value);
+        result = m_Item->putAndInsertOFStringArray(DCM_StudyInstanceUID, value);
     return result;
 }
 
-
-OFCondition IODGeneralStudyModule::setStudyDate(const OFString &value,
-                                                const OFBool checkValue)
+OFCondition IODGeneralStudyModule::setStudyDate(const OFString& value, const OFBool checkValue)
 {
     OFCondition result = (checkValue) ? DcmDate::checkStringValue(value, "1") : EC_Normal;
     if (result.good())
-      result =  m_Item->putAndInsertOFStringArray(DCM_StudyDate, value);
+        result = m_Item->putAndInsertOFStringArray(DCM_StudyDate, value);
     return result;
 }
 
-
-OFCondition IODGeneralStudyModule::setStudyTime(const OFString &value,
-                                                const OFBool checkValue)
+OFCondition IODGeneralStudyModule::setStudyTime(const OFString& value, const OFBool checkValue)
 {
     OFCondition result = (checkValue) ? DcmTime::checkStringValue(value, "1") : EC_Normal;
     if (result.good())
-      result =  m_Item->putAndInsertOFStringArray(DCM_StudyTime,value);
+        result = m_Item->putAndInsertOFStringArray(DCM_StudyTime, value);
     return result;
 }
 
-
-OFCondition IODGeneralStudyModule::setStudyID(const OFString &value,
-                                              const OFBool checkValue)
+OFCondition IODGeneralStudyModule::setStudyID(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result =  m_Item->putAndInsertOFStringArray(DCM_StudyID, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_StudyID, value);
+    return result;
 }
 
-
-OFCondition IODGeneralStudyModule::setAccessionNumber(const OFString &value,
-                                                      const OFBool checkValue)
+OFCondition IODGeneralStudyModule::setAccessionNumber(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result =  m_Item->putAndInsertOFStringArray(DCM_AccessionNumber, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_AccessionNumber, value);
+    return result;
 }
-
index 44ee42318e6f938b9e1456ca1c7959da74fe8088..aa923315e1a1d89d4529dff7e149ba7af4b1ab69 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2017, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modhelp.h"
-#include "dcmtk/dcmdata/dcitem.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmdata/dcdeftag.h"
-
+#include "dcmtk/dcmdata/dcitem.h"
 
 // List of tags within the Patient Module
-const DcmTagKey DcmModuleHelpers::patientModuleTags[] =
-{
-  DCM_PatientName,
-  DCM_PatientID,
-  // Macro IssuerOfPatientIDMacro
-  DCM_IssuerOfPatientID,
-  DCM_IssuerOfPatientIDQualifiersSequence,
-  // EndMacro IssuerOfPatientIDMacro
-  DCM_PatientBirthDate,
-  DCM_PatientSex,
-  DCM_QualityControlSubject,
-  DCM_ReferencedPatientSequence,
-  DCM_PatientBirthTime,
-  DCM_RETIRED_OtherPatientIDs,
-  DCM_OtherPatientIDsSequence,
-  DCM_OtherPatientNames,
-  DCM_EthnicGroup,
-  DCM_PatientComments,
-  DCM_PatientSpeciesDescription,
-  DCM_PatientSpeciesCodeSequence,
-  DCM_PatientBreedDescription,
-  DCM_PatientBreedCodeSequence,
-  DCM_BreedRegistrationSequence,
-  DCM_ResponsiblePerson,
-  DCM_ResponsiblePersonRole,
-  DCM_ResponsibleOrganization,
-  DCM_PatientIdentityRemoved,
-  DCM_DeidentificationMethod,
-  DCM_DeidentificationMethodCodeSequence
-};
+const DcmTagKey DcmModuleHelpers::patientModuleTags[] = { DCM_PatientName,
+                                                          DCM_PatientID,
+                                                          // Macro IssuerOfPatientIDMacro
+                                                          DCM_IssuerOfPatientID,
+                                                          DCM_IssuerOfPatientIDQualifiersSequence,
+                                                          // EndMacro IssuerOfPatientIDMacro
+                                                          DCM_PatientBirthDate,
+                                                          DCM_PatientSex,
+                                                          DCM_QualityControlSubject,
+                                                          DCM_ReferencedPatientSequence,
+                                                          DCM_PatientBirthTime,
+                                                          DCM_RETIRED_OtherPatientIDs,
+                                                          DCM_OtherPatientIDsSequence,
+                                                          DCM_OtherPatientNames,
+                                                          DCM_EthnicGroup,
+                                                          DCM_PatientComments,
+                                                          DCM_PatientSpeciesDescription,
+                                                          DCM_PatientSpeciesCodeSequence,
+                                                          DCM_PatientBreedDescription,
+                                                          DCM_PatientBreedCodeSequence,
+                                                          DCM_BreedRegistrationSequence,
+                                                          DCM_ResponsiblePerson,
+                                                          DCM_ResponsiblePersonRole,
+                                                          DCM_ResponsibleOrganization,
+                                                          DCM_PatientIdentityRemoved,
+                                                          DCM_DeidentificationMethod,
+                                                          DCM_DeidentificationMethodCodeSequence };
 
 // List of tags within the Clinical Trial Subject Module
-const DcmTagKey DcmModuleHelpers::clinicalTrialSubjectModuleTags[] =
-{
-  DCM_ClinicalTrialSponsorName,
-  DCM_ClinicalTrialProtocolID,
-  DCM_ClinicalTrialProtocolName,
-  DCM_ClinicalTrialSiteID,
-  DCM_ClinicalTrialSiteName,
-  DCM_ClinicalTrialSubjectID,
-  DCM_ClinicalTrialSubjectReadingID,
-  DCM_ClinicalTrialProtocolEthicsCommitteeName,
-  DCM_ClinicalTrialProtocolEthicsCommitteeApprovalNumber
-};
+const DcmTagKey DcmModuleHelpers::clinicalTrialSubjectModuleTags[]
+    = { DCM_ClinicalTrialSponsorName,
+        DCM_ClinicalTrialProtocolID,
+        DCM_ClinicalTrialProtocolName,
+        DCM_ClinicalTrialSiteID,
+        DCM_ClinicalTrialSiteName,
+        DCM_ClinicalTrialSubjectID,
+        DCM_ClinicalTrialSubjectReadingID,
+        DCM_ClinicalTrialProtocolEthicsCommitteeName,
+        DCM_ClinicalTrialProtocolEthicsCommitteeApprovalNumber };
 
 // List of tags within the General Study Module
-const DcmTagKey DcmModuleHelpers::generalStudyModuleTags[] =
-{
-  DCM_StudyInstanceUID,
-  DCM_StudyDate,
-  DCM_StudyTime,
-  DCM_ReferringPhysicianName,
-  DCM_ReferringPhysicianIdentificationSequence,
-  DCM_StudyID,
-  DCM_AccessionNumber,
-  DCM_IssuerOfAccessionNumberSequence,
-  DCM_StudyDescription,
-  DCM_PhysiciansOfRecord,
-  DCM_PhysiciansOfRecordIdentificationSequence,
-  DCM_NameOfPhysiciansReadingStudy,
-  DCM_PhysiciansReadingStudyIdentificationSequence,
-  DCM_RequestingServiceCodeSequence,
-  DCM_ReferencedStudySequence,
-  DCM_ProcedureCodeSequence,
-  DCM_ReasonForPerformedProcedureCodeSequence
-};
+const DcmTagKey DcmModuleHelpers::generalStudyModuleTags[] = { DCM_StudyInstanceUID,
+                                                               DCM_StudyDate,
+                                                               DCM_StudyTime,
+                                                               DCM_ReferringPhysicianName,
+                                                               DCM_ReferringPhysicianIdentificationSequence,
+                                                               DCM_StudyID,
+                                                               DCM_AccessionNumber,
+                                                               DCM_IssuerOfAccessionNumberSequence,
+                                                               DCM_StudyDescription,
+                                                               DCM_PhysiciansOfRecord,
+                                                               DCM_PhysiciansOfRecordIdentificationSequence,
+                                                               DCM_NameOfPhysiciansReadingStudy,
+                                                               DCM_PhysiciansReadingStudyIdentificationSequence,
+                                                               DCM_RequestingServiceCodeSequence,
+                                                               DCM_ReferencedStudySequence,
+                                                               DCM_ProcedureCodeSequence,
+                                                               DCM_ReasonForPerformedProcedureCodeSequence };
 
 // List of tags within the Patient Study Module
-const DcmTagKey DcmModuleHelpers::patientStudyModuleTags[] =
-{
-  DCM_AdmittingDiagnosesDescription,
-  DCM_AdmittingDiagnosesCodeSequence,
-  DCM_PatientAge,
-  DCM_PatientSize,
-  DCM_PatientWeight,
-  DCM_PatientSizeCodeSequence,
-  DCM_Occupation,
-  DCM_AdditionalPatientHistory,
-  DCM_AdmissionID,
-  DCM_IssuerOfAdmissionIDSequence,
-  DCM_ServiceEpisodeID,
-  DCM_IssuerOfServiceEpisodeIDSequence,
-  DCM_ServiceEpisodeDescription,
-  DCM_PatientSexNeutered
-};
+const DcmTagKey DcmModuleHelpers::patientStudyModuleTags[] = { DCM_AdmittingDiagnosesDescription,
+                                                               DCM_AdmittingDiagnosesCodeSequence,
+                                                               DCM_PatientAge,
+                                                               DCM_PatientSize,
+                                                               DCM_PatientWeight,
+                                                               DCM_PatientSizeCodeSequence,
+                                                               DCM_Occupation,
+                                                               DCM_AdditionalPatientHistory,
+                                                               DCM_AdmissionID,
+                                                               DCM_IssuerOfAdmissionIDSequence,
+                                                               DCM_ServiceEpisodeID,
+                                                               DCM_IssuerOfServiceEpisodeIDSequence,
+                                                               DCM_ServiceEpisodeDescription,
+                                                               DCM_PatientSexNeutered };
 
 // List of tags within the Clinical Trial Study Module
-const DcmTagKey DcmModuleHelpers::clinicalTrialStudyModuleTags[] =
-{
-  DCM_ClinicalTrialTimePointID,
-  DCM_ClinicalTrialTimePointDescription,
-  DCM_ConsentForClinicalTrialUseSequence
-};
+const DcmTagKey DcmModuleHelpers::clinicalTrialStudyModuleTags[]
+    = { DCM_ClinicalTrialTimePointID, DCM_ClinicalTrialTimePointDescription, DCM_ConsentForClinicalTrialUseSequence };
 
 // List of tags within the General Series Module
-const DcmTagKey DcmModuleHelpers::generalSeriesModuleTags[] =
-{
-  DCM_Modality,
-  DCM_SeriesInstanceUID,
-  DCM_SeriesNumber,
-  DCM_Laterality,
-  DCM_SeriesDate,
-  DCM_SeriesTime,
-  DCM_PerformingPhysicianName,
-  DCM_PerformingPhysicianIdentificationSequence,
-  DCM_ProtocolName,
-  DCM_SeriesDescription,
-  DCM_SeriesDescriptionCodeSequence,
-  DCM_OperatorsName,
-  DCM_OperatorIdentificationSequence,
-  DCM_ReferencedPerformedProcedureStepSequence,
-  DCM_RelatedSeriesSequence,
-  DCM_BodyPartExamined,
-  DCM_PatientPosition,
-  DCM_SmallestPixelValueInSeries,
-  DCM_LargestPixelValueInSeries,
-  DCM_RequestAttributesSequence,
-  // Macro PerformedProcedureStepSummaryMacro
-  DCM_PerformedProcedureStepID,
-  DCM_PerformedProcedureStepStartDate,
-  DCM_PerformedProcedureStepStartTime,
-  DCM_PerformedProcedureStepEndDate,
-  DCM_PerformedProcedureStepEndTime,
-  DCM_PerformedProcedureStepDescription,
-  DCM_PerformedProtocolCodeSequence,
-  DCM_CommentsOnThePerformedProcedureStep,
-  // EndMacro PerformedProcedureStepSummaryMacro
-  DCM_AnatomicalOrientationType
-};
+const DcmTagKey DcmModuleHelpers::generalSeriesModuleTags[] = { DCM_Modality,
+                                                                DCM_SeriesInstanceUID,
+                                                                DCM_SeriesNumber,
+                                                                DCM_Laterality,
+                                                                DCM_SeriesDate,
+                                                                DCM_SeriesTime,
+                                                                DCM_PerformingPhysicianName,
+                                                                DCM_PerformingPhysicianIdentificationSequence,
+                                                                DCM_ProtocolName,
+                                                                DCM_SeriesDescription,
+                                                                DCM_SeriesDescriptionCodeSequence,
+                                                                DCM_OperatorsName,
+                                                                DCM_OperatorIdentificationSequence,
+                                                                DCM_ReferencedPerformedProcedureStepSequence,
+                                                                DCM_RelatedSeriesSequence,
+                                                                DCM_BodyPartExamined,
+                                                                DCM_PatientPosition,
+                                                                DCM_SmallestPixelValueInSeries,
+                                                                DCM_LargestPixelValueInSeries,
+                                                                DCM_RequestAttributesSequence,
+                                                                // Macro PerformedProcedureStepSummaryMacro
+                                                                DCM_PerformedProcedureStepID,
+                                                                DCM_PerformedProcedureStepStartDate,
+                                                                DCM_PerformedProcedureStepStartTime,
+                                                                DCM_PerformedProcedureStepEndDate,
+                                                                DCM_PerformedProcedureStepEndTime,
+                                                                DCM_PerformedProcedureStepDescription,
+                                                                DCM_PerformedProtocolCodeSequence,
+                                                                DCM_CommentsOnThePerformedProcedureStep,
+                                                                // EndMacro PerformedProcedureStepSummaryMacro
+                                                                DCM_AnatomicalOrientationType };
 
 // List of tags within the Clinical Trial Series Module
-const DcmTagKey DcmModuleHelpers::clinicalTrialSeriesModuleTags[] =
-{
-  DCM_ClinicalTrialCoordinatingCenterName,
-  DCM_ClinicalTrialSeriesID,
-  DCM_ClinicalTrialSeriesDescription
-};
+const DcmTagKey DcmModuleHelpers::clinicalTrialSeriesModuleTags[]
+    = { DCM_ClinicalTrialCoordinatingCenterName, DCM_ClinicalTrialSeriesID, DCM_ClinicalTrialSeriesDescription };
 
 // List of tags within the General Equipment Module
-const DcmTagKey DcmModuleHelpers::generalEquipmentModuleTags[] =
-{
-  DCM_Manufacturer,
-  DCM_InstitutionName,
-  DCM_InstitutionAddress,
-  DCM_StationName,
-  DCM_InstitutionalDepartmentName,
-  DCM_ManufacturerModelName,
-  DCM_DeviceSerialNumber,
-  DCM_SoftwareVersions,
-  DCM_GantryID,
-  DCM_SpatialResolution,
-  DCM_DateOfLastCalibration,
-  DCM_TimeOfLastCalibration,
-  DCM_PixelPaddingValue
-};
+const DcmTagKey DcmModuleHelpers::generalEquipmentModuleTags[] = { DCM_Manufacturer,
+                                                                   DCM_InstitutionName,
+                                                                   DCM_InstitutionAddress,
+                                                                   DCM_StationName,
+                                                                   DCM_InstitutionalDepartmentName,
+                                                                   DCM_ManufacturerModelName,
+                                                                   DCM_DeviceSerialNumber,
+                                                                   DCM_SoftwareVersions,
+                                                                   DCM_GantryID,
+                                                                   DCM_SpatialResolution,
+                                                                   DCM_DateOfLastCalibration,
+                                                                   DCM_TimeOfLastCalibration,
+                                                                   DCM_PixelPaddingValue };
 
 // List of tags within the Frame of Reference Module
-const DcmTagKey DcmModuleHelpers::frameOfReferenceModuleTags[] =
-{
-  DCM_FrameOfReferenceUID,
-  DCM_PositionReferenceIndicator
-};
+const DcmTagKey DcmModuleHelpers::frameOfReferenceModuleTags[]
+    = { DCM_FrameOfReferenceUID, DCM_PositionReferenceIndicator };
 
 // List of tags within the SOP Common Module, excluding Digital Signatures Macro
-const DcmTagKey DcmModuleHelpers::sopCommonModuleTags[] =
-{
-  DCM_SOPClassUID,
-  DCM_SOPInstanceUID,
-  DCM_SpecificCharacterSet,
-  DCM_InstanceCreationDate,
-  DCM_InstanceCreationTime,
-  DCM_InstanceCoercionDateTime,
-  DCM_InstanceCreatorUID,
-  DCM_RelatedGeneralSOPClassUID,
-  DCM_OriginalSpecializedSOPClassUID,
-  DCM_CodingSchemeIdentificationSequence,
-  DCM_TimezoneOffsetFromUTC,
-  DCM_ContributingEquipmentSequence,
-  DCM_InstanceNumber,
-  DCM_SOPInstanceStatus,
-  DCM_SOPAuthorizationDateTime,
-  DCM_SOPAuthorizationComment,
-  DCM_AuthorizationEquipmentCertificationNumber,
-  // Macro DigitalSignaturesMacro
-  //DCM_MACParametersSequence,
-  //DCM_DigitalSignaturesSequence,
-  // EndMacro DigitalSignaturesMacro
-  DCM_EncryptedAttributesSequence,
-  DCM_OriginalAttributesSequence,
-  DCM_HL7StructuredDocumentReferenceSequence,
-  DCM_LongitudinalTemporalInformationModified,
-  DCM_QueryRetrieveView,
-  DCM_ConversionSourceAttributesSequence
-};
+const DcmTagKey DcmModuleHelpers::sopCommonModuleTags[] = { DCM_SOPClassUID,
+                                                            DCM_SOPInstanceUID,
+                                                            DCM_SpecificCharacterSet,
+                                                            DCM_InstanceCreationDate,
+                                                            DCM_InstanceCreationTime,
+                                                            DCM_InstanceCoercionDateTime,
+                                                            DCM_InstanceCreatorUID,
+                                                            DCM_RelatedGeneralSOPClassUID,
+                                                            DCM_OriginalSpecializedSOPClassUID,
+                                                            DCM_CodingSchemeIdentificationSequence,
+                                                            DCM_TimezoneOffsetFromUTC,
+                                                            DCM_ContributingEquipmentSequence,
+                                                            DCM_InstanceNumber,
+                                                            DCM_SOPInstanceStatus,
+                                                            DCM_SOPAuthorizationDateTime,
+                                                            DCM_SOPAuthorizationComment,
+                                                            DCM_AuthorizationEquipmentCertificationNumber,
+                                                            // Macro DigitalSignaturesMacro
+                                                            // DCM_MACParametersSequence,
+                                                            // DCM_DigitalSignaturesSequence,
+                                                            // EndMacro DigitalSignaturesMacro
+                                                            DCM_EncryptedAttributesSequence,
+                                                            DCM_OriginalAttributesSequence,
+                                                            DCM_HL7StructuredDocumentReferenceSequence,
+                                                            DCM_LongitudinalTemporalInformationModified,
+                                                            DCM_QueryRetrieveView,
+                                                            DCM_ConversionSourceAttributesSequence };
 
 // List of tags within the General Image Module
-const DcmTagKey DcmModuleHelpers::generalImageModuleTags[] =
-{
-  DCM_InstanceNumber,
-  DCM_PatientOrientation,
-  DCM_ContentDate,
-  DCM_ContentTime,
-  DCM_ImageType,
-  DCM_AcquisitionNumber,
-  DCM_AcquisitionDate,
-  DCM_AcquisitionTime,
-  DCM_AcquisitionDateTime,
-  DCM_ReferencedImageSequence,
-  DCM_DerivationDescription,
-  DCM_DerivationCodeSequence,
-  DCM_SourceImageSequence,
-  DCM_ReferencedInstanceSequence,
-  DCM_ImagesInAcquisition,
-  DCM_ImageComments,
-  DCM_QualityControlImage,
-  DCM_BurnedInAnnotation,
-  DCM_RecognizableVisualFeatures,
-  DCM_LossyImageCompression,
-  DCM_LossyImageCompressionRatio,
-  DCM_LossyImageCompressionMethod,
-  DCM_IconImageSequence,
-  DCM_PresentationLUTShape,
-  DCM_IrradiationEventUID,
-  DCM_RealWorldValueMappingSequence
-};
-
+const DcmTagKey DcmModuleHelpers::generalImageModuleTags[] = { DCM_InstanceNumber,
+                                                               DCM_PatientOrientation,
+                                                               DCM_ContentDate,
+                                                               DCM_ContentTime,
+                                                               DCM_ImageType,
+                                                               DCM_AcquisitionNumber,
+                                                               DCM_AcquisitionDate,
+                                                               DCM_AcquisitionTime,
+                                                               DCM_AcquisitionDateTime,
+                                                               DCM_ReferencedImageSequence,
+                                                               DCM_DerivationDescription,
+                                                               DCM_DerivationCodeSequence,
+                                                               DCM_SourceImageSequence,
+                                                               DCM_ReferencedInstanceSequence,
+                                                               DCM_ImagesInAcquisition,
+                                                               DCM_ImageComments,
+                                                               DCM_QualityControlImage,
+                                                               DCM_BurnedInAnnotation,
+                                                               DCM_RecognizableVisualFeatures,
+                                                               DCM_LossyImageCompression,
+                                                               DCM_LossyImageCompressionRatio,
+                                                               DCM_LossyImageCompressionMethod,
+                                                               DCM_IconImageSequence,
+                                                               DCM_PresentationLUTShape,
+                                                               DCM_IrradiationEventUID,
+                                                               DCM_RealWorldValueMappingSequence };
 
 void DcmModuleHelpers::copyElement(const DcmTagKey& tag, DcmItem& src, DcmItem& dest)
 {
-  DcmElement *delem;
-  OFCondition cond;
-  // get (deep) copy of element
-  cond = src.findAndGetElement(tag, delem, OFFalse /*searchIntoSub*/, OFTrue /*createCopy*/);
-  if (cond.good())
-  {
-    // and insert into destination item
-    cond = dest.insert(delem, OFTrue);
-    if (cond.bad())
+    DcmElement* delem;
+    OFCondition cond;
+    // get (deep) copy of element
+    cond = src.findAndGetElement(tag, delem, OFFalse /*searchIntoSub*/, OFTrue /*createCopy*/);
+    if (cond.good())
     {
-      // we do not expect any errors here, so report it
-      DCMDATA_ERROR("Could not insert element with tag " << tag << " into item: " << cond.text());
+        // and insert into destination item
+        cond = dest.insert(delem, OFTrue);
+        if (cond.bad())
+        {
+            // we do not expect any errors here, so report it
+            DCMDATA_ERROR("Could not insert element with tag " << tag << " into item: " << cond.text());
+        }
     }
-  }
 }
 
-template<size_t N>
-inline void DcmModuleHelpers::copyModule( const DcmTagKey (&tags)[N], DcmItem& src, DcmItem& dest )
+template <size_t N>
+inline void DcmModuleHelpers::copyModule(const DcmTagKey (&tags)[N], DcmItem& src, DcmItem& dest)
 {
-  for (const DcmTagKey* it = tags, * const end = tags + N; it != end; ++it)
-    DcmModuleHelpers::copyElement(*it, src, dest);
+    for (const DcmTagKey *it = tags, *const end = tags + N; it != end; ++it)
+        DcmModuleHelpers::copyElement(*it, src, dest);
 }
 
-
 void DcmModuleHelpers::copyPatientModule(DcmItem& src, DcmItem& dest)
 {
-  copyModule(patientModuleTags, src, dest);
+    copyModule(patientModuleTags, src, dest);
 }
 
-
 void DcmModuleHelpers::copyClinicalTrialSubjectModule(DcmItem& src, DcmItem& dest)
 {
-  copyModule(clinicalTrialSubjectModuleTags, src, dest);
+    copyModule(clinicalTrialSubjectModuleTags, src, dest);
 }
 
-
 void DcmModuleHelpers::copyGeneralStudyModule(DcmItem& src, DcmItem& dest)
 {
-  copyModule(generalStudyModuleTags, src, dest);
+    copyModule(generalStudyModuleTags, src, dest);
 }
 
-
 void DcmModuleHelpers::copyPatientStudyModule(DcmItem& src, DcmItem& dest)
 {
-  copyModule(patientStudyModuleTags, src, dest);
+    copyModule(patientStudyModuleTags, src, dest);
 }
 
-
 void DcmModuleHelpers::copyClinicalTrialStudyModule(DcmItem& src, DcmItem& dest)
 {
-  copyModule(clinicalTrialStudyModuleTags, src, dest);
+    copyModule(clinicalTrialStudyModuleTags, src, dest);
 }
 
-
 void DcmModuleHelpers::copyGeneralSeriesModule(DcmItem& src, DcmItem& dest)
 {
-  copyModule(generalSeriesModuleTags, src, dest);
+    copyModule(generalSeriesModuleTags, src, dest);
 }
 
-
 void DcmModuleHelpers::copyClinicalTrialSeriesModule(DcmItem& src, DcmItem& dest)
 {
-  copyModule(clinicalTrialSeriesModuleTags, src, dest);
+    copyModule(clinicalTrialSeriesModuleTags, src, dest);
 }
 
-
 void DcmModuleHelpers::copyGeneralEquipmentModule(DcmItem& src, DcmItem& dest)
 {
-  copyModule(generalEquipmentModuleTags, src, dest);
+    copyModule(generalEquipmentModuleTags, src, dest);
 }
 
-
 void DcmModuleHelpers::copyFrameOfReferenceModule(DcmItem& src, DcmItem& dest)
 {
-  copyModule(frameOfReferenceModuleTags, src, dest);
+    copyModule(frameOfReferenceModuleTags, src, dest);
 }
 
-
 void DcmModuleHelpers::copySOPCommonModule(DcmItem& src, DcmItem& dest)
 {
-  copyModule(sopCommonModuleTags, src, dest);
+    copyModule(sopCommonModuleTags, src, dest);
 }
 
-
 void DcmModuleHelpers::copyGeneralImageModule(DcmItem& src, DcmItem& dest)
 {
-  copyModule(generalImageModuleTags, src, dest);
+    copyModule(generalImageModuleTags, src, dest);
 }
index 8d0b7b2060d0c28acb93bd96d4a07b2f2c51f261..056098469e0424262a9690bf84029965361870f0 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016-2017, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modimagepixel.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmdata/dcdeftag.h"
-#include "dcmtk/dcmdata/dcvrobow.h"
 #include "dcmtk/dcmdata/dcvrcs.h"
 #include "dcmtk/dcmdata/dcvris.h"
+#include "dcmtk/dcmdata/dcvrobow.h"
 #include "dcmtk/dcmiod/iodutil.h"
 
-template<typename T>
+template <typename T>
 const OFString IODImagePixelModule<T>::m_ModuleName = "ImagePixelModule";
-template<typename T>
+template <typename T>
 const DcmTagKey IODImagePixelModule<T>::pixel_data_tag = DCM_PixelData;
 
-template<typename T>
-IODImagePixelModule<T>::IODImagePixelModule(OFshared_ptr<DcmItem> item,
-                                            OFshared_ptr<IODRules> rules)
-: IODImagePixelBase(item, rules)
+template <typename T>
+IODImagePixelModule<T>::IODImagePixelModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODImagePixelBase(item, rules)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-template<typename T>
+template <typename T>
 OFString IODImagePixelModule<T>::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-template<typename T>
+template <typename T>
 IODImagePixelModule<T>::IODImagePixelModule()
-: IODImagePixelBase()
+    : IODImagePixelBase()
 {
-  resetRules();
+    resetRules();
 }
 
-template<typename T>
+template <typename T>
 IODImagePixelModule<T>::~IODImagePixelModule()
 {
 }
 
-template<typename T>
+template <typename T>
 void IODImagePixelModule<T>::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_SamplesPerPixel, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PhotometricInterpretation, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_Rows, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_Columns, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_BitsAllocated, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_BitsStored, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_HighBit, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PixelRepresentation, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PlanarConfiguration, "1", "1C", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PixelAspectRatio, "2", "1C", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ICCProfile, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_SamplesPerPixel, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PhotometricInterpretation, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_Rows, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_Columns, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_BitsAllocated, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_BitsStored, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_HighBit, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PixelRepresentation, "1", "1", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PlanarConfiguration, "1", "1C", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PixelAspectRatio, "2", "1C", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ICCProfile, "1", "3", getName(), DcmIODTypes::IE_IMAGE), OFTrue);
 }
 
-template<typename T>
-OFCondition IODImagePixelModule<T>::read(DcmItem& source,
-                                         const OFBool clearOldData)
+template <typename T>
+OFCondition IODImagePixelModule<T>::read(DcmItem& source, const OFBool clearOldData)
 {
-  // Read common attributes
-  IODImagePixelBase::read(source, clearOldData);
-  // Read extra attributes of Image Pixel Module
-  IODModule::read(source, clearOldData);
-  return EC_Normal;
+    // Read common attributes
+    IODImagePixelBase::read(source, clearOldData);
+    // Read extra attributes of Image Pixel Module
+    IODModule::read(source, clearOldData);
+    return EC_Normal;
 }
 
-template<typename T>
+template <typename T>
 OFCondition IODImagePixelModule<T>::write(DcmItem& destination)
 {
-  // Write common attributes
-  OFCondition result = IODImagePixelBase::write(destination);
-  // Write extra attributes of Image Pixel Module
-  if (result.good())
-  {
-    IODModule::write(destination);
-  }
-  return result;
+    // Write common attributes
+    OFCondition result = IODImagePixelBase::write(destination);
+    // Write extra attributes of Image Pixel Module
+    if (result.good())
+    {
+        IODModule::write(destination);
+    }
+    return result;
 }
 
-template<typename T>
+template <typename T>
 IODImagePixelBase::DataType IODImagePixelModule<T>::getDataType() const
 {
-  return IODImagePixelBase::DATA_TYPE_INTEGER;
+    return IODImagePixelBase::DATA_TYPE_INTEGER;
 }
 
-template<typename T>
-OFCondition IODImagePixelModule<T>::getBitsStored(Uint16& value,
-                                                  const signed long pos)
+template <typename T>
+OFCondition IODImagePixelModule<T>::getBitsStored(Uint16& value, const unsigned long pos)
 {
-  return m_Item->findAndGetUint16(DCM_BitsStored, value, pos);
+    return m_Item->findAndGetUint16(DCM_BitsStored, value, pos);
 }
 
-template<typename T>
-OFCondition IODImagePixelModule<T>::getHighBit(Uint16& value,
-                                            const signed long pos)
+template <typename T>
+OFCondition IODImagePixelModule<T>::getHighBit(Uint16& value, const unsigned long pos)
 {
-  return m_Item->findAndGetUint16(DCM_HighBit, value, pos);
+    return m_Item->findAndGetUint16(DCM_HighBit, value, pos);
 }
 
-template<typename T>
-OFCondition IODImagePixelModule<T>::getPixelRepresentation(Uint16& value,
-                                                        const signed long pos)
+template <typename T>
+OFCondition IODImagePixelModule<T>::getPixelRepresentation(Uint16& value, const unsigned long pos)
 {
-  return m_Item->findAndGetUint16(DCM_PixelRepresentation, value, pos);
+    return m_Item->findAndGetUint16(DCM_PixelRepresentation, value, pos);
 }
 
-template<typename T>
-OFCondition IODImagePixelModule<T>::getPlanarConfiguration(Uint16& value,
-                                                         const signed long pos)
+template <typename T>
+OFCondition IODImagePixelModule<T>::getPlanarConfiguration(Uint16& value, const unsigned long pos)
 {
-  return m_Item->findAndGetUint16(DCM_PlanarConfiguration, value, pos);
+    return m_Item->findAndGetUint16(DCM_PlanarConfiguration, value, pos);
 }
 
-template<typename T>
+template <typename T>
 OFCondition IODImagePixelModule<T>::getICCProfile(OFVector<Uint8>& values)
 {
-  DcmElement* elem = NULL;
-  OFCondition result = m_Item->findAndGetElement(DCM_ICCProfile, elem);
-  if (result.good())
-  {
-    DcmOtherByteOtherWord* ob = OFstatic_cast(DcmOtherByteOtherWord*, elem);
-    if (ob)
-      return DcmIODUtil::copyFromUint8Array<OFVector<Uint8> > (ob, values);
+    DcmElement* elem   = NULL;
+    OFCondition result = m_Item->findAndGetElement(DCM_ICCProfile, elem);
+    if (result.good())
+    {
+        DcmOtherByteOtherWord* ob = OFstatic_cast(DcmOtherByteOtherWord*, elem);
+        if (ob)
+            return DcmIODUtil::copyFromUint8Array<OFVector<Uint8> >(ob, values);
+        else
+            return EC_InternalError;
+    }
     else
-      return EC_InternalError;
-  }
-  else
-    return EC_TagNotFound;
+        return EC_TagNotFound;
 }
 
-template<typename T>
-OFCondition IODImagePixelModule<T>::setSamplesPerPixel(const Uint16 value,
-                                                    const OFBool checkValue)
+template <typename T>
+OFCondition IODImagePixelModule<T>::setSamplesPerPixel(const Uint16 value, const OFBool checkValue)
 {
-  OFCondition result = EC_Normal;
+    OFCondition result = EC_Normal;
 
-  // only values 1, 3 and 4 (retired) are permitted
-  if (checkValue)
-  {
-    if ( (value == 0) || (value == 2) || (value > 4) )
+    // only values 1, 3 and 4 (retired) are permitted
+    if (checkValue)
     {
-      DCMIOD_ERROR("Value " << value << " not permitted for attribute Samples Per Pixel");
-      result = EC_InvalidValue;
+        if ((value == 0) || (value == 2) || (value > 4))
+        {
+            DCMIOD_ERROR("Value " << value << " not permitted for attribute Samples Per Pixel");
+            result = EC_InvalidValue;
+        }
+        else if (value == 4)
+        {
+            DCMIOD_WARN("Value " << value << " is retired for attribute Samples Per Pixel");
+        }
     }
-    else if (value == 4)
-    {
-      DCMIOD_WARN("Value " << value << " is retired for attribute Samples Per Pixel");
-    }
-  }
 
-  if (result.good() )
-    result = m_Item->putAndInsertUint16(DCM_SamplesPerPixel, value);
+    if (result.good())
+        result = m_Item->putAndInsertUint16(DCM_SamplesPerPixel, value);
 
-  return result;
+    return result;
 }
 
-template<typename T>
-OFCondition IODImagePixelModule<T>::setPhotometricInterpretation(const OFString& value,
-                                                              const OFBool checkValue)
+template <typename T>
+OFCondition IODImagePixelModule<T>::setPhotometricInterpretation(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_PhotometricInterpretation, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_PhotometricInterpretation, value);
+    return result;
 }
 
-template<typename T>
-OFCondition IODImagePixelModule<T>::setBitsAllocated(const Uint16 value,
-                                                  const OFBool checkValue)
+template <typename T>
+OFCondition IODImagePixelModule<T>::setBitsAllocated(const Uint16 value, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertUint16(DCM_BitsAllocated, value);
+    (void)checkValue;
+    return m_Item->putAndInsertUint16(DCM_BitsAllocated, value);
 }
 
-template<typename T>
-OFCondition IODImagePixelModule<T>::setBitsStored(const Uint16 value,
-                                               const OFBool checkValue)
+template <typename T>
+OFCondition IODImagePixelModule<T>::setBitsStored(const Uint16 value, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertUint16(DCM_BitsStored, value);
+    (void)checkValue;
+    return m_Item->putAndInsertUint16(DCM_BitsStored, value);
 }
 
-template<typename T>
-OFCondition IODImagePixelModule<T>::setHighBit(const Uint16 value,
-                                            const OFBool checkValue)
+template <typename T>
+OFCondition IODImagePixelModule<T>::setHighBit(const Uint16 value, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertUint16(DCM_HighBit, value);
+    (void)checkValue;
+    return m_Item->putAndInsertUint16(DCM_HighBit, value);
 }
 
-template<typename T>
-OFCondition IODImagePixelModule<T>::setPixelRepresentation(const Uint16 value,
-                                                        const OFBool checkValue)
+template <typename T>
+OFCondition IODImagePixelModule<T>::setPixelRepresentation(const Uint16 value, const OFBool checkValue)
 {
-  OFCondition result = EC_Normal;
-  if (checkValue)
-  {
-    if ( (value != 0) && (value != 1) )
+    OFCondition result = EC_Normal;
+    if (checkValue)
+    {
+        if ((value != 0) && (value != 1))
+        {
+            DCMIOD_ERROR("Value " << value << " not permitted for attribute Pixel Representation");
+            result = EC_InvalidValue;
+        }
+    }
+    if (result.good())
     {
-      DCMIOD_ERROR("Value " << value << " not permitted for attribute Pixel Representation");
-      result = EC_InvalidValue;
+        result = m_Item->putAndInsertUint16(DCM_PixelRepresentation, value);
     }
-  }
-  if ( result.good() )
-  {
-   result = m_Item->putAndInsertUint16(DCM_PixelRepresentation, value);
-  }
-  return result;
+    return result;
 }
 
-template<typename T>
-OFCondition IODImagePixelModule<T>::setPlanarConfiguration(const Uint16 value,
-                                                        const OFBool checkValue)
+template <typename T>
+OFCondition IODImagePixelModule<T>::setPlanarConfiguration(const Uint16 value, const OFBool checkValue)
 {
-  OFCondition result = EC_Normal;
-  if (checkValue)
-  {
-    if ( (value != 0) && (value != 1) )
+    OFCondition result = EC_Normal;
+    if (checkValue)
+    {
+        if ((value != 0) && (value != 1))
+        {
+            DCMIOD_ERROR("Value " << value << " not permitted for attribute Planar Configuration");
+            result = EC_InvalidValue;
+        }
+    }
+    if (result.good())
     {
-      DCMIOD_ERROR("Value " << value << " not permitted for attribute Planar Configuration");
-      result = EC_InvalidValue;
+        result = m_Item->putAndInsertUint16(DCM_PlanarConfiguration, value);
     }
-  }
-  if ( result.good() )
-  {
-    result = m_Item->putAndInsertUint16(DCM_PlanarConfiguration, value);
-  }
-  return result;
+    return result;
 }
 
-template<typename T>
-OFCondition IODImagePixelModule<T>::setICCProfile(const Uint8* values,
-                                               const size_t length)
+template <typename T>
+OFCondition IODImagePixelModule<T>::setICCProfile(const Uint8* values, const size_t length)
 {
-  return m_Item->putAndInsertUint8Array(DCM_ICCProfile, values, OFstatic_cast(unsigned long, length));
+    return m_Item->putAndInsertUint8Array(DCM_ICCProfile, values, OFstatic_cast(unsigned long, length));
 }
 
 template class IODImagePixelModule<Uint8>;
index f35725e5f90a15d9d05a9f7bc0a1efe8ebd1efdd..cd83c7be7888b3f334bba238d4c19240b3b27f69 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  *  Author: Michael Onken
  *
- *  Purpose: Base class for Image Pixel Module and related (e.g. Ploating Point)
+ *  Purpose: Base class for Image Pixel Module and related (e.g. Floating Point)
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modimagepixelbase.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmdata/dcdeftag.h"
-#include "dcmtk/dcmdata/dcvrobow.h"
 #include "dcmtk/dcmdata/dcvrcs.h"
 #include "dcmtk/dcmdata/dcvris.h"
+#include "dcmtk/dcmdata/dcvrobow.h"
 #include "dcmtk/dcmiod/iodutil.h"
 
 const OFString IODImagePixelBase::m_ModuleName = "ImagePixelBase";
 
-
-IODImagePixelBase::IODImagePixelBase(OFshared_ptr<DcmItem> item,
-                                     OFshared_ptr<IODRules> rules)
-: IODModule(item, rules)
+IODImagePixelBase::IODImagePixelBase(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODModule(item, rules)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 OFString IODImagePixelBase::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 IODImagePixelBase::IODImagePixelBase()
-: IODModule()
+    : IODModule()
 {
-  resetRules();
+    resetRules();
 }
 
-
 IODImagePixelBase::~IODImagePixelBase()
 {
 }
 
-
 void IODImagePixelBase::resetRules()
 {
-  // all rules in sub classes
+    // all rules in sub classes
 }
 
-
-OFCondition IODImagePixelBase::getSamplesPerPixel(Uint16 &value,
-                                         const signed long pos)
+OFCondition IODImagePixelBase::getSamplesPerPixel(Uint16& value, const unsigned long pos)
 {
-  return m_Item->findAndGetUint16(DCM_SamplesPerPixel, value, pos);
+    return m_Item->findAndGetUint16(DCM_SamplesPerPixel, value, pos);
 }
 
-
-OFCondition IODImagePixelBase::getPhotometricInterpretation(OFString&value,
-                                                      const signed long pos)
+OFCondition IODImagePixelBase::getPhotometricInterpretation(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_PhotometricInterpretation, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_PhotometricInterpretation, *m_Item, value, pos);
 }
 
-
-OFCondition IODImagePixelBase::getRows(Uint16& value,
-                                 const signed long pos)
+OFCondition IODImagePixelBase::getRows(Uint16& value, const unsigned long pos)
 {
-  return m_Item->findAndGetUint16(DCM_Rows, value, pos);
+    return m_Item->findAndGetUint16(DCM_Rows, value, pos);
 }
 
-
-OFCondition IODImagePixelBase::getColumns(Uint16& value,
-                                    const signed long pos)
+OFCondition IODImagePixelBase::getColumns(Uint16& value, const unsigned long pos)
 {
-  return m_Item->findAndGetUint16(DCM_Columns, value, pos);
+    return m_Item->findAndGetUint16(DCM_Columns, value, pos);
 }
 
-
-OFCondition IODImagePixelBase::getBitsAllocated(Uint16& value,
-                                          const signed long pos)
+OFCondition IODImagePixelBase::getBitsAllocated(Uint16& value, const unsigned long pos)
 {
-  return m_Item->findAndGetUint16(DCM_BitsAllocated, value, pos);
+    return m_Item->findAndGetUint16(DCM_BitsAllocated, value, pos);
 }
 
-
-OFCondition IODImagePixelBase::getPixelAspectRatio(Uint16& value,
-                                            const signed long pos)
+OFCondition IODImagePixelBase::getPixelAspectRatio(Uint16& value, const unsigned long pos)
 {
-  return m_Item->findAndGetUint16(DCM_PixelAspectRatio, value, pos);
+    return m_Item->findAndGetUint16(DCM_PixelAspectRatio, value, pos);
 }
 
-
-OFCondition IODImagePixelBase::setRows(const Uint16 value,
-                                         const OFBool checkValue)
+OFCondition IODImagePixelBase::setRows(const Uint16 value, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertUint16(DCM_Rows, value);
+    (void)checkValue;
+    return m_Item->putAndInsertUint16(DCM_Rows, value);
 }
 
-
-OFCondition IODImagePixelBase::setColumns(const Uint16 value,
-                                            const OFBool checkValue)
+OFCondition IODImagePixelBase::setColumns(const Uint16 value, const OFBool checkValue)
 {
-  (void)checkValue;
-  return m_Item->putAndInsertUint16(DCM_Columns, value);
+    (void)checkValue;
+    return m_Item->putAndInsertUint16(DCM_Columns, value);
 }
 
-
 OFCondition IODImagePixelBase::setPixelAspectRatio(const OFString& verticalPixelSize,
-                                                     const OFString& horizontalPixelSize,
-                                                     const OFBool checkValue)
+                                                   const OFString& horizontalPixelSize,
+                                                   const OFBool checkValue)
 {
-  OFString concat = verticalPixelSize;
-  concat += "\\"; concat += horizontalPixelSize;
-  OFCondition cond;
-  if (checkValue)
-  {
-    cond = DcmIntegerString::checkStringValue(concat, "2");
-    // check for unsignedness, too?
-  }
-  if (cond.good()) m_Item->putAndInsertOFStringArray(DCM_PixelAspectRatio, concat);
-  return cond;
+    OFString concat = verticalPixelSize;
+    concat += "\\";
+    concat += horizontalPixelSize;
+    OFCondition cond;
+    if (checkValue)
+    {
+        cond = DcmIntegerString::checkStringValue(concat, "2");
+        // check for unsignedness, too?
+    }
+    if (cond.good())
+        m_Item->putAndInsertOFStringArray(DCM_PixelAspectRatio, concat);
+    return cond;
 }
index 906cafcd626278dd7bcde870c6655503163c5890..de0c2318097b40f3ee9e5be4890af0b1ac348e5b 100644 (file)
  *
  */
 
-#include "dcmtk/config/osconfig.h"
 #include "dcmtk/dcmiod/modmultiframedimension.h"
+#include "dcmtk/config/osconfig.h"
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmdata/dcpath.h" // for private tag reservation checking
 #include "dcmtk/dcmdata/dcvrat.h"
+#include "dcmtk/dcmdata/dcvrcs.h"
 #include "dcmtk/dcmdata/dcvrlo.h"
 #include "dcmtk/dcmdata/dcvrui.h"
-#include "dcmtk/dcmdata/dcvrcs.h"
-#include "dcmtk/dcmdata/dcpath.h" // for private tag reservation checking
 #include "dcmtk/dcmiod/iodutil.h" // for static helpers
 
 const OFString IODMultiframeDimensionModule::m_ModuleName = "MultiframeDimensionModule";
 
-
-IODMultiframeDimensionModule::IODMultiframeDimensionModule(OFshared_ptr<DcmItem> data,
-                                                           OFshared_ptr<IODRules> rules) :
-  IODModule(data, rules),
-  m_DimensionIndexSequence(),
-  m_DimensionOrganizationSequence()
+IODMultiframeDimensionModule::IODMultiframeDimensionModule(OFshared_ptr<DcmItem> data, OFshared_ptr<IODRules> rules)
+    : IODModule(data, rules)
+    , m_DimensionIndexSequence()
+    , m_DimensionOrganizationSequence()
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODMultiframeDimensionModule::IODMultiframeDimensionModule()
-: IODModule(),
-  m_DimensionIndexSequence(),
-  m_DimensionOrganizationSequence()
+    : IODModule()
+    , m_DimensionIndexSequence()
+    , m_DimensionOrganizationSequence()
 {
-  resetRules();
+    resetRules();
 }
 
-
 OFCondition IODMultiframeDimensionModule::addDimensionIndex(const DcmTagKey& dimensionIndexPointer,
                                                             const OFString& dimensionOrganizationUID,
                                                             const DcmTagKey& functionalGroupPointer,
@@ -59,591 +55,599 @@ OFCondition IODMultiframeDimensionModule::addDimensionIndex(const DcmTagKey& dim
                                                             const OFString& dimensionIndexPrivateCreator,
                                                             const OFString& functionalGroupPrivateCreator)
 {
-  if ( (dimensionIndexPointer.isPrivate() && dimensionIndexPrivateCreator.empty()) ||
-       (functionalGroupPointer.isPrivate() && functionalGroupPrivateCreator.empty()) )
-  {
-    DCMIOD_ERROR("Cannot add private Dimension Index without private creator");
-    return IOD_EC_MissingAttribute;
-  }
-
-  if (dimensionOrganizationUID.empty())
-  {
-    DCMIOD_ERROR("Cannot add Dimension Index without Dimension Organization UID");
-    return IOD_EC_MissingAttribute;
-  }
-
-  // Add Dimension Organization by its UID if such organization does not exist yet
-  OFVector<DimensionOrganizationItem*>::iterator it = m_DimensionOrganizationSequence.begin();
-  while (it != m_DimensionOrganizationSequence.end())
-  {
-    OFString val;
-    (*it)->getDimensionOrganizationUID(val);
-    if (val == dimensionOrganizationUID)
+    if ((dimensionIndexPointer.isPrivate() && dimensionIndexPrivateCreator.empty())
+        || (functionalGroupPointer.isPrivate() && functionalGroupPrivateCreator.empty()))
     {
-      break;
+        DCMIOD_ERROR("Cannot add private Dimension Index without private creator");
+        return IOD_EC_MissingAttribute;
     }
-    it++;
-  }
-  OFCondition result;
-  if (it == m_DimensionOrganizationSequence.end())
-  {
-    DimensionOrganizationItem* item = new DimensionOrganizationItem;
-    if (item == NULL)
+
+    if (dimensionOrganizationUID.empty())
     {
-      return EC_MemoryExhausted;
+        DCMIOD_ERROR("Cannot add Dimension Index without Dimension Organization UID");
+        return IOD_EC_MissingAttribute;
     }
-    result = item->setDimensionOrganizationUID(dimensionOrganizationUID);
-    if (result.bad())
-      return result;
-    m_DimensionOrganizationSequence.push_back(item);
-  }
 
-  // Create dimension and add it to this object
-  DimensionIndexItem* dim = new DimensionIndexItem();
-  if (!dim)
-    return EC_MemoryExhausted;
+    // Add Dimension Organization by its UID if such organization does not exist yet
+    OFVector<DimensionOrganizationItem*>::iterator it = m_DimensionOrganizationSequence.begin();
+    while (it != m_DimensionOrganizationSequence.end())
+    {
+        OFString val;
+        (*it)->getDimensionOrganizationUID(val);
+        if (val == dimensionOrganizationUID)
+        {
+            break;
+        }
+        it++;
+    }
+    OFCondition result;
+    if (it == m_DimensionOrganizationSequence.end())
+    {
+        DimensionOrganizationItem* item = new DimensionOrganizationItem;
+        if (item == NULL)
+        {
+            return EC_MemoryExhausted;
+        }
+        result = item->setDimensionOrganizationUID(dimensionOrganizationUID);
+        if (result.bad())
+            return result;
+        m_DimensionOrganizationSequence.push_back(item);
+    }
 
-  result = dim->setDimensionOrganizationUID(dimensionOrganizationUID);
-  if (result.good()) result = dim->setFunctionalGroupPointer(functionalGroupPointer);
-  if (result.good()) result = dim->setDimensionIndexPointer(dimensionIndexPointer);
-  if (result.good() && !dimensionIndexPrivateCreator.empty()) dim->setDimensionIndexPrivateCreator(dimensionIndexPrivateCreator);
-  if (result.good() && !functionalGroupPrivateCreator.empty()) dim->setFunctionalGroupPrivateCreator(functionalGroupPrivateCreator);
-  if (result.good() && !dimensionDescriptionLabel.empty()) dim->setDimensionDescriptionLabel(dimensionDescriptionLabel);
-  if (result.bad())
-  {
-    DCMIOD_ERROR("Could not add Dimension Index: Invalid data values");
-    delete dim;
-  }
-  m_DimensionIndexSequence.push_back(dim);
+    // Create dimension and add it to this object
+    DimensionIndexItem* dim = new DimensionIndexItem();
+    if (!dim)
+        return EC_MemoryExhausted;
+
+    result = dim->setDimensionOrganizationUID(dimensionOrganizationUID);
+    if (result.good())
+        result = dim->setFunctionalGroupPointer(functionalGroupPointer);
+    if (result.good())
+        result = dim->setDimensionIndexPointer(dimensionIndexPointer);
+    if (result.good() && !dimensionIndexPrivateCreator.empty())
+        dim->setDimensionIndexPrivateCreator(dimensionIndexPrivateCreator);
+    if (result.good() && !functionalGroupPrivateCreator.empty())
+        dim->setFunctionalGroupPrivateCreator(functionalGroupPrivateCreator);
+    if (result.good() && !dimensionDescriptionLabel.empty())
+        dim->setDimensionDescriptionLabel(dimensionDescriptionLabel);
+    if (result.bad())
+    {
+        DCMIOD_ERROR("Could not add Dimension Index: Invalid data values");
+        delete dim;
+    }
+    m_DimensionIndexSequence.push_back(dim);
 
-  return result;
+    return result;
 }
 
-
 OFString IODMultiframeDimensionModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 void IODMultiframeDimensionModule::clearData()
 {
-  DcmIODUtil::freeContainer(m_DimensionIndexSequence);
-  IODComponent::clearData();
+    DcmIODUtil::freeContainer(m_DimensionIndexSequence);
+    IODComponent::clearData();
 }
 
-
-
-OFCondition IODMultiframeDimensionModule::read(DcmItem& source,
-                                               const OFBool clearOldData)
+OFCondition IODMultiframeDimensionModule::read(DcmItem& source, const OFBool clearOldData)
 {
-  if (clearOldData)
-    clearData();
+    if (clearOldData)
+        clearData();
 
-  IODComponent::read(source, OFFalse /* data already cleared above */);
+    IODComponent::read(source, OFFalse /* data already cleared above */);
 
-  DcmIODUtil::readSubSequence(source, DCM_DimensionIndexSequence, m_DimensionIndexSequence, m_Rules->getByTag(DCM_DimensionIndexSequence));
-  DcmIODUtil::readSubSequence(source, DCM_DimensionOrganizationSequence, m_DimensionOrganizationSequence, m_Rules->getByTag(DCM_DimensionOrganizationSequence));
+    DcmIODUtil::readSubSequence(
+        source, DCM_DimensionIndexSequence, m_DimensionIndexSequence, m_Rules->getByTag(DCM_DimensionIndexSequence));
+    DcmIODUtil::readSubSequence(source,
+                                DCM_DimensionOrganizationSequence,
+                                m_DimensionOrganizationSequence,
+                                m_Rules->getByTag(DCM_DimensionOrganizationSequence));
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 OFCondition IODMultiframeDimensionModule::write(DcmItem& destination)
 {
-  OFCondition result = EC_Normal;
+    OFCondition result = EC_Normal;
 
-  // Re-create dimension organization data
-  createDimensionOrganizationData();
-  DcmIODUtil::writeSubSequence<OFVector<DimensionOrganizationItem*> >(result, DCM_DimensionOrganizationSequence, m_DimensionOrganizationSequence, *m_Item, m_Rules->getByTag(DCM_DimensionOrganizationSequence));
+    // Re-create dimension organization data
+    createDimensionOrganizationData();
+    DcmIODUtil::writeSubSequence<OFVector<DimensionOrganizationItem*> >(
+        result,
+        DCM_DimensionOrganizationSequence,
+        m_DimensionOrganizationSequence,
+        *m_Item,
+        m_Rules->getByTag(DCM_DimensionOrganizationSequence));
 
-  DcmIODUtil::writeSubSequence<OFVector<DimensionIndexItem*> >(result, DCM_DimensionIndexSequence, m_DimensionIndexSequence, *m_Item, m_Rules->getByTag(DCM_DimensionIndexSequence));
+    DcmIODUtil::writeSubSequence<OFVector<DimensionIndexItem*> >(result,
+                                                                 DCM_DimensionIndexSequence,
+                                                                 m_DimensionIndexSequence,
+                                                                 *m_Item,
+                                                                 m_Rules->getByTag(DCM_DimensionIndexSequence));
 
-  result = IODComponent::write(destination);
-  return result;
+    result = IODComponent::write(destination);
+    return result;
 }
 
-
 void IODMultiframeDimensionModule::resetRules()
 {
-  // Parameters for Rule are tag, VM, type (1,1C,2,2C,3), module name and logical IOD level
-  m_Rules->addRule(new IODRule(DCM_DimensionOrganizationSequence, "1-n", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_DimensionOrganizationType, "1", "3", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_DimensionIndexSequence, "1-n", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    // Parameters for Rule are tag, VM, type (1,1C,2,2C,3), module name and logical IOD level
+    m_Rules->addRule(new IODRule(DCM_DimensionOrganizationSequence, "1-n", "1", getName(), DcmIODTypes::IE_INSTANCE),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_DimensionOrganizationType, "1", "3", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_DimensionIndexSequence, "1-n", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
 }
 
-
 OFCondition IODMultiframeDimensionModule::checkDimensions(DcmItem* fgItem)
 {
-  if (fgItem == NULL)
-  {
-    fgItem = &getData();
-  }
-
-  DcmSequenceOfItems *perFrame = NULL;
-  if (fgItem->findAndGetSequence(DCM_PerFrameFunctionalGroupsSequence, perFrame).bad())
-  {
-    DCMIOD_WARN("Will not check dimension consistency with functional groups (no per-frame functional groups found)");
-  }
-
-  OFCondition result;
-  OFVector<IODMultiframeDimensionModule::DimensionIndexItem*>::iterator dim = m_DimensionIndexSequence.begin();
-  size_t errors = 0;
-  size_t dimNo = 1;
-  while (dim != m_DimensionIndexSequence.end())
-  {
-    DcmTagKey indexPointer;
-    result = (*dim)->getDimensionIndexPointer(indexPointer);
-    if (result.bad())
+    if (fgItem == NULL)
     {
-      DCMIOD_ERROR("Dimension " << dimNo <<  " does not provide a dimension index pointer");
-      errors++;
+        fgItem = &getData();
     }
-    OFString uid;
-    result = (*dim)->getDimensionOrganizationUID(uid);
-    if (result.bad())
-    {
-      DCMIOD_ERROR("Dimension " << dimNo <<  " does not provide a dimension organization UID");
-      errors++;
-    }
-    DcmTagKey fgPointer;
-    result = (*dim)->getFunctionalGroupPointer(fgPointer);
-    if (result.bad())
-    {
-      DCMIOD_ERROR("Dimension " << dimNo <<  " does not provide a functional group pointer");
-      errors++;
-    }
-    OFString privateCreator;
-    if (indexPointer.isPrivate() && (indexPointer != DCM_UndefinedTagKey) )
-    {
-      result = (*dim)->getDimensionIndexPrivateCreator(privateCreator);
-      if (result.bad())
-      {
-        DCMIOD_ERROR("Dimension " << dimNo <<  " has private index pointer " << indexPointer << " but private creator is not set");
-        errors++;
-      }
-    }
-    OFString privateFGCreator;
-    if (fgPointer.isPrivate() && (fgPointer != DCM_UndefinedTagKey))
+
+    DcmSequenceOfItems* perFrame = NULL;
+    if (fgItem->findAndGetSequence(DCM_PerFrameFunctionalGroupsSequence, perFrame).bad())
     {
-      result = (*dim)->getFunctionalGroupPrivateCreator(privateFGCreator);
-      if (result.bad())
-      {
-        DCMIOD_ERROR("Dimension " << dimNo <<  " has private fg group pointer " << fgPointer << " but private creator is not set");
-        errors++;
-      }
+        DCMIOD_WARN(
+            "Will not check dimension consistency with functional groups (no per-frame functional groups found)");
     }
 
-    if (perFrame && (fgPointer != DCM_UndefinedTagKey) && (indexPointer != DCM_UndefinedTagKey) )
+    OFCondition result;
+    OFVector<IODMultiframeDimensionModule::DimensionIndexItem*>::iterator dim = m_DimensionIndexSequence.begin();
+    size_t errors                                                             = 0;
+    size_t dimNo                                                              = 1;
+    while (dim != m_DimensionIndexSequence.end())
     {
-      if (!getIndexElement(perFrame, fgPointer, indexPointer, privateFGCreator, privateCreator))
-      {
-        errors++;
-      }
-    }
+        DcmTagKey indexPointer;
+        result = (*dim)->getDimensionIndexPointer(indexPointer);
+        if (result.bad())
+        {
+            DCMIOD_ERROR("Dimension " << dimNo << " does not provide a dimension index pointer");
+            errors++;
+        }
+        OFString uid;
+        result = (*dim)->getDimensionOrganizationUID(uid);
+        if (result.bad())
+        {
+            DCMIOD_ERROR("Dimension " << dimNo << " does not provide a dimension organization UID");
+            errors++;
+        }
+        DcmTagKey fgPointer;
+        result = (*dim)->getFunctionalGroupPointer(fgPointer);
+        if (result.bad())
+        {
+            DCMIOD_ERROR("Dimension " << dimNo << " does not provide a functional group pointer");
+            errors++;
+        }
+        OFString privateCreator;
+        if (indexPointer.isPrivate() && (indexPointer != DCM_UndefinedTagKey))
+        {
+            result = (*dim)->getDimensionIndexPrivateCreator(privateCreator);
+            if (result.bad())
+            {
+                DCMIOD_ERROR("Dimension " << dimNo << " has private index pointer " << indexPointer
+                                          << " but private creator is not set");
+                errors++;
+            }
+        }
+        OFString privateFGCreator;
+        if (fgPointer.isPrivate() && (fgPointer != DCM_UndefinedTagKey))
+        {
+            result = (*dim)->getFunctionalGroupPrivateCreator(privateFGCreator);
+            if (result.bad())
+            {
+                DCMIOD_ERROR("Dimension " << dimNo << " has private fg group pointer " << fgPointer
+                                          << " but private creator is not set");
+                errors++;
+            }
+        }
+
+        if (perFrame && (fgPointer != DCM_UndefinedTagKey) && (indexPointer != DCM_UndefinedTagKey))
+        {
+            if (!getIndexElement(perFrame, fgPointer, indexPointer, privateFGCreator, privateCreator))
+            {
+                errors++;
+            }
+        }
 
-    dim++;
-  }
+        dim++;
+    }
 
-  if (errors > 0)
-    return IOD_EC_InvalidDimensions;
-  else
-    return EC_Normal;
+    if (errors > 0)
+        return IOD_EC_InvalidDimensions;
+    else
+        return EC_Normal;
 }
 
-
-DcmElement* IODMultiframeDimensionModule::getIndexElement(DcmSequenceOfItems *perFrameFG,
+DcmElement* IODMultiframeDimensionModule::getIndexElement(DcmSequenceOfItems* perFrameFG,
                                                           const DcmTagKey& fgPointer,
                                                           const DcmTagKey& indexPointer,
-                                                          const OFString&  fgPrivateCreator,
-                                                          const OFString&  privateCreator)
-{
-  if (perFrameFG == NULL)
-  {
-    DCMIOD_ERROR("Cannot get Dimension Index: No per-frame functional groups are provided");
-    return NULL; // nothing to do
-  }
-
-  size_t numFrames = perFrameFG->card();
-  OFCondition result;
-  DcmElement *returnValue = NULL;
-  for (size_t count = 0; count < numFrames; count++)
-  {
-    DcmItem* item = perFrameFG->getItem(OFstatic_cast(unsigned long, count));
-    if (item != NULL)
+                                                          const OFString& fgPrivateCreator,
+                                                          const OFString& privateCreator)
+{
+    if (perFrameFG == NULL)
     {
-      // Check for the functional group mentioned in dimension
-      DcmSequenceOfItems *fgSequence = NULL;
-      if (item->findAndGetSequence(fgPointer, fgSequence).good())
-      {
-        // Check private reservation for fg if necessary
-        if (fgPointer.isPrivate())
-        {
-          result = DcmPathProcessor::checkPrivateTagReservation(item, fgPointer, fgPrivateCreator);
-          if (result.bad())
-          {
-            DCMIOD_ERROR("Cannot get Dimension Index for frame " << count << ": " << result.text());
-          }
-        }
-        // Check whether actual fg information exists (single item in related fg sequence)
-        DcmItem *fgItem = fgSequence->getItem(0);
-        if (fgItem != NULL)
+        DCMIOD_ERROR("Cannot get Dimension Index: No per-frame functional groups are provided");
+        return NULL; // nothing to do
+    }
+
+    size_t numFrames = perFrameFG->card();
+    OFCondition result;
+    DcmElement* returnValue = NULL;
+    for (size_t count = 0; count < numFrames; count++)
+    {
+        DcmItem* item = perFrameFG->getItem(OFstatic_cast(unsigned long, count));
+        if (item != NULL)
         {
-          if (fgItem->findAndGetElement(indexPointer, returnValue).good())
-          {
-            if (returnValue->getTag().isPrivate())
+            // Check for the functional group mentioned in dimension
+            DcmSequenceOfItems* fgSequence = NULL;
+            if (item->findAndGetSequence(fgPointer, fgSequence).good())
             {
-              if (!privateCreator.empty())
-              {
-                result = DcmPathProcessor::checkPrivateTagReservation(fgItem, indexPointer, privateCreator);
-                if (result.bad())
+                // Check private reservation for fg if necessary
+                if (fgPointer.isPrivate())
+                {
+                    result = DcmPathProcessor::checkPrivateTagReservation(item, fgPointer, fgPrivateCreator);
+                    if (result.bad())
+                    {
+                        DCMIOD_ERROR("Cannot get Dimension Index for frame " << count << ": " << result.text());
+                    }
+                }
+                // Check whether actual fg information exists (single item in related fg sequence)
+                DcmItem* fgItem = fgSequence->getItem(0);
+                if (fgItem != NULL)
                 {
-                  DCMIOD_ERROR("Cannot get Dimension Index for frame " << count << ": " << result.text());
+                    if (fgItem->findAndGetElement(indexPointer, returnValue).good())
+                    {
+                        if (returnValue->getTag().isPrivate())
+                        {
+                            if (!privateCreator.empty())
+                            {
+                                result = DcmPathProcessor::checkPrivateTagReservation(
+                                    fgItem, indexPointer, privateCreator);
+                                if (result.bad())
+                                {
+                                    DCMIOD_ERROR("Cannot get Dimension Index for frame " << count << ": "
+                                                                                         << result.text());
+                                }
+                            }
+                            else
+                            {
+                                DCMIOD_ERROR("Cannot get Dimension Index since fg "
+                                             << fgPointer << " misses reservation for frame " << count << ": "
+                                             << result.text());
+                            }
+                        }
+                    }
+                    else
+                    {
+                        DCMIOD_ERROR("Cannot get Dimension Index since fg "
+                                     << fgPointer << " does not contain index pointer attribute " << indexPointer
+                                     << " for frame " << count);
+                    }
                 }
-              }
-              else
-              {
-                DCMIOD_ERROR("Cannot get Dimension Index since fg " << fgPointer << " misses reservation for frame " << count << ": " << result.text());
-              }
+                else
+                {
+                    DCMIOD_ERROR("Cannot get Dimension Index since fg " << fgPointer << " does have any data for frame "
+                                                                        << count);
+                }
+            }
+            else
+            {
+                DCMIOD_ERROR("Cannot get Dimension Index since fg " << fgPointer << " does not exist for frame "
+                                                                    << count);
             }
-          }
-          else
-          {
-            DCMIOD_ERROR("Cannot get Dimension Index since fg " << fgPointer << " does not contain index pointer attribute " << indexPointer << " for frame " << count);
-          }
         }
         else
         {
-          DCMIOD_ERROR("Cannot get Dimension Index since fg " << fgPointer << " does have any data for frame " << count);
+            DCMIOD_ERROR("Cannot get Dimension Index: since no per-frame functional group for frame " << count
+                                                                                                      << " exists");
         }
-      }
-      else
-      {
-        DCMIOD_ERROR("Cannot get Dimension Index since fg " << fgPointer << " does not exist for frame " << count);
-      }
-    }
-    else
-    {
-      DCMIOD_ERROR("Cannot get Dimension Index: since no per-frame functional group for frame " << count << " exists");
     }
-  }
 
-  return returnValue;
+    return returnValue;
 }
 
-
-
 void IODMultiframeDimensionModule::createDimensionOrganizationData()
 {
-  // Clear old data
-  DcmIODUtil::freeContainer(m_DimensionOrganizationSequence);
-  // Collect dimensions from all Dimension Index Pointers
-  OFVector<DimensionIndexItem*>::iterator item = m_DimensionIndexSequence.begin();
-  while (item != m_DimensionIndexSequence.end())
-  {
-    OFCondition result;
-    // Make sure every UID is only added once
-    OFBool isNew = OFTrue;
-    OFString existinguid, newuid;
-    (*item)->getDimensionOrganizationUID(newuid);
-    OFVector<DimensionOrganizationItem*>::iterator existing = m_DimensionOrganizationSequence.begin();
-    while (existing != m_DimensionOrganizationSequence.end())
-    {
-      (*existing)->getDimensionOrganizationUID(existinguid);
-      if (existinguid == newuid)
-      {
-        isNew = OFFalse;
-        break;
-      }
-      existing++;
-    }
-    if (isNew)
+    // Clear old data
+    DcmIODUtil::freeContainer(m_DimensionOrganizationSequence);
+    // Collect dimensions from all Dimension Index Pointers
+    OFVector<DimensionIndexItem*>::iterator item = m_DimensionIndexSequence.begin();
+    while (item != m_DimensionIndexSequence.end())
     {
-      DimensionOrganizationItem* uidItem = new DimensionOrganizationItem();
-      if (!uidItem)
-      {
-        DCMIOD_ERROR("Memory Exhausted while collecting Dimension Organziation UIDs");
-        return;
-      }
-      result = uidItem->setDimensionOrganizationUID(newuid);
-      if (result.good())
-      {
-        m_DimensionOrganizationSequence.push_back(uidItem);
-      }
-      else
-      {
-        DCMIOD_ERROR("Could not set Dimension Organization UID " << newuid << ": " << result.text());
-        delete uidItem;
-        return;
-      }
+        OFCondition result;
+        // Make sure every UID is only added once
+        OFBool isNew = OFTrue;
+        OFString existinguid, newuid;
+        (*item)->getDimensionOrganizationUID(newuid);
+        OFVector<DimensionOrganizationItem*>::iterator existing = m_DimensionOrganizationSequence.begin();
+        while (existing != m_DimensionOrganizationSequence.end())
+        {
+            (*existing)->getDimensionOrganizationUID(existinguid);
+            if (existinguid == newuid)
+            {
+                isNew = OFFalse;
+                break;
+            }
+            existing++;
+        }
+        if (isNew)
+        {
+            DimensionOrganizationItem* uidItem = new DimensionOrganizationItem();
+            if (!uidItem)
+            {
+                DCMIOD_ERROR("Memory Exhausted while collecting Dimension Organziation UIDs");
+                return;
+            }
+            result = uidItem->setDimensionOrganizationUID(newuid);
+            if (result.good())
+            {
+                m_DimensionOrganizationSequence.push_back(uidItem);
+            }
+            else
+            {
+                DCMIOD_ERROR("Could not set Dimension Organization UID " << newuid << ": " << result.text());
+                delete uidItem;
+                return;
+            }
+        }
+        item++;
     }
-    item++;
-  }
 }
 
-
-OFCondition IODMultiframeDimensionModule::getDimensionOrganizationType(OFString& value,
-                                                                       const long signed int pos) const
+OFCondition IODMultiframeDimensionModule::getDimensionOrganizationType(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_DimensionOrganizationType, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_DimensionOrganizationType, *m_Item, value, pos);
 }
 
-
-OFCondition IODMultiframeDimensionModule::setDimensionOrganizationType(const OFString& value,
-                                                                       const OFBool checkValue)
+OFCondition IODMultiframeDimensionModule::setDimensionOrganizationType(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_DimensionOrganizationType, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_DimensionOrganizationType, value);
+    return result;
 }
 
-
-OFVector< IODMultiframeDimensionModule::DimensionIndexItem* >& IODMultiframeDimensionModule::getDimensionIndexSequence()
+OFVector<IODMultiframeDimensionModule::DimensionIndexItem*>& IODMultiframeDimensionModule::getDimensionIndexSequence()
 {
-  return m_DimensionIndexSequence;
+    return m_DimensionIndexSequence;
 }
 
-OFVector< IODMultiframeDimensionModule::DimensionOrganizationItem* >& IODMultiframeDimensionModule::getDimensionOrganizationSequence()
+OFVector<IODMultiframeDimensionModule::DimensionOrganizationItem*>&
+IODMultiframeDimensionModule::getDimensionOrganizationSequence()
 {
-  return m_DimensionOrganizationSequence;
+    return m_DimensionOrganizationSequence;
 }
 
 IODMultiframeDimensionModule::~IODMultiframeDimensionModule()
 {
-  DcmIODUtil::freeContainer(m_DimensionIndexSequence);
-  DcmIODUtil::freeContainer(m_DimensionOrganizationSequence);
+    DcmIODUtil::freeContainer(m_DimensionIndexSequence);
+    DcmIODUtil::freeContainer(m_DimensionOrganizationSequence);
 }
 
-
 IODMultiframeDimensionModule::DimensionIndexItem::DimensionIndexItem(OFshared_ptr<DcmItem> data,
-                                                                                   OFshared_ptr<IODRules> rules,
-                                                                                   IODComponent* parent)
-: IODComponent(data, rules, parent)
+                                                                     OFshared_ptr<IODRules> rules,
+                                                                     IODComponent* parent)
+    : IODComponent(data, rules, parent)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-IODMultiframeDimensionModule::DimensionIndexItem::DimensionIndexItem(IODComponent* parent):
-IODComponent(parent)
+IODMultiframeDimensionModule::DimensionIndexItem::DimensionIndexItem(IODComponent* parent)
+    : IODComponent(parent)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODMultiframeDimensionModule::DimensionIndexItem::~DimensionIndexItem()
 {
-  // Nothing to do
+    // Nothing to do
 }
 
-
 void IODMultiframeDimensionModule::DimensionIndexItem::resetRules()
 {
-  // Concatenation attributes
-  m_Rules->addRule(new IODRule(DCM_DimensionIndexPointer, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_DimensionIndexPrivateCreator, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_FunctionalGroupPointer, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_FunctionalGroupPrivateCreator, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_DimensionOrganizationUID, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_DimensionDescriptionLabel, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    // Concatenation attributes
+    m_Rules->addRule(new IODRule(DCM_DimensionIndexPointer, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_DimensionIndexPrivateCreator, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_FunctionalGroupPointer, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_FunctionalGroupPrivateCreator, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_DimensionOrganizationUID, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_DimensionDescriptionLabel, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE),
+                     OFTrue);
 }
 
-
 OFString IODMultiframeDimensionModule::DimensionIndexItem::getName() const
 {
-  return "DimensionIndexSequence";
+    return "DimensionIndexSequence";
 }
 
-
-OFCondition IODMultiframeDimensionModule::DimensionIndexItem::getDimensionDescriptionLabel(OFString& value,
-                                                                                                  const long signed int pos) const
+OFCondition
+IODMultiframeDimensionModule::DimensionIndexItem::getDimensionDescriptionLabel(OFString& value,
+                                                                               const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_DimensionDescriptionLabel, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_DimensionDescriptionLabel, *m_Item, value, pos);
 }
 
-
 OFCondition IODMultiframeDimensionModule::DimensionIndexItem::getDimensionIndexPointer(DcmTagKey& value,
-                                                                                              const long signed int pos) const
-{
-  OFString tagstr;
-  DcmIODUtil::getStringValueFromItem(DCM_DimensionIndexPointer, *m_Item, tagstr, pos);
-  value = DcmIODUtil::parseTagKey(tagstr);
-  if (value == DCM_UndefinedTagKey)
-    return EC_TagNotFound;
-  else
-    return EC_Normal;
+                                                                                       const long signed int pos) const
+{
+    OFString tagstr;
+    DcmIODUtil::getStringValueFromItem(DCM_DimensionIndexPointer, *m_Item, tagstr, pos);
+    value = DcmIODUtil::parseTagKey(tagstr);
+    if (value == DCM_UndefinedTagKey)
+        return EC_TagNotFound;
+    else
+        return EC_Normal;
 }
 
-
-OFCondition IODMultiframeDimensionModule::DimensionIndexItem::getDimensionIndexPrivateCreator(OFString& value,
-                                                                                                     const long signed int pos) const
+OFCondition
+IODMultiframeDimensionModule::DimensionIndexItem::getDimensionIndexPrivateCreator(OFString& value,
+                                                                                  const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_DimensionIndexPrivateCreator, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_DimensionIndexPrivateCreator, *m_Item, value, pos);
 }
 
-
-OFCondition IODMultiframeDimensionModule::DimensionIndexItem::getDimensionOrganizationUID(OFString& value,
-                                                                                                 const long signed int pos) const
+OFCondition
+IODMultiframeDimensionModule::DimensionIndexItem::getDimensionOrganizationUID(OFString& value,
+                                                                              const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_DimensionOrganizationUID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_DimensionOrganizationUID, *m_Item, value, pos);
 }
 
-
 OFCondition IODMultiframeDimensionModule::DimensionIndexItem::getFunctionalGroupPointer(DcmTagKey& value,
-                                                                                               const long signed int pos) const
-{
-  OFString tagstr;
-  DcmIODUtil::getStringValueFromItem(DCM_FunctionalGroupPointer, *m_Item, tagstr, pos);
-  value = DcmIODUtil::parseTagKey(tagstr);
-  if (value == DCM_UndefinedTagKey)
-    return EC_TagNotFound;
-  else
-    return EC_Normal;
+                                                                                        const long signed int pos) const
+{
+    OFString tagstr;
+    DcmIODUtil::getStringValueFromItem(DCM_FunctionalGroupPointer, *m_Item, tagstr, pos);
+    value = DcmIODUtil::parseTagKey(tagstr);
+    if (value == DCM_UndefinedTagKey)
+        return EC_TagNotFound;
+    else
+        return EC_Normal;
 }
 
-
-OFCondition IODMultiframeDimensionModule::DimensionIndexItem::getFunctionalGroupPrivateCreator(OFString& value,
-                                                                                                      const long signed int pos) const
+OFCondition
+IODMultiframeDimensionModule::DimensionIndexItem::getFunctionalGroupPrivateCreator(OFString& value,
+                                                                                   const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_FunctionalGroupPrivateCreator, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_FunctionalGroupPrivateCreator, *m_Item, value, pos);
 }
 
-
 OFCondition IODMultiframeDimensionModule::DimensionIndexItem::setDimensionDescriptionLabel(const OFString& value,
-                                                                                                  const OFBool checkValue)
+                                                                                           const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_DimensionDescriptionLabel, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_DimensionDescriptionLabel, value);
+    return result;
 }
 
-
 OFCondition IODMultiframeDimensionModule::DimensionIndexItem::setFunctionalGroupPointer(const DcmTagKey& value,
                                                                                         const OFBool checkValue)
 {
-  (void)checkValue;
-  if (value == DCM_UndefinedTagKey)
-    return EC_IllegalParameter;
+    (void)checkValue;
+    if (value == DCM_UndefinedTagKey)
+        return EC_IllegalParameter;
 
-  DcmAttributeTag *elem = OFstatic_cast(DcmAttributeTag*, DcmItem::newDicomElement(DCM_FunctionalGroupPointer));
-  if (elem == NULL)
-    return EC_InternalError;
+    DcmAttributeTag* elem = OFstatic_cast(DcmAttributeTag*, DcmItem::newDicomElement(DCM_FunctionalGroupPointer));
+    if (elem == NULL)
+        return EC_InternalError;
 
-  OFCondition result;
-  Uint16 *attrTagArray;
-  result = elem->putTagVal(value);
-  if (result.good()) result = elem->getUint16Array(attrTagArray);
-  if (result.good()) result = m_Item->putAndInsertUint16Array(DCM_FunctionalGroupPointer, attrTagArray, 1);
-  delete elem;
+    OFCondition result;
+    Uint16* attrTagArray;
+    result = elem->putTagVal(value);
+    if (result.good())
+        result = elem->getUint16Array(attrTagArray);
+    if (result.good())
+        result = m_Item->putAndInsertUint16Array(DCM_FunctionalGroupPointer, attrTagArray, 1);
+    delete elem;
 
-  return result;
+    return result;
 }
 
-
 OFCondition IODMultiframeDimensionModule::DimensionIndexItem::setFunctionalGroupPrivateCreator(const OFString& value,
-                                                                                                      const OFBool checkValue)
+                                                                                               const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_FunctionalGroupPrivateCreator, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_FunctionalGroupPrivateCreator, value);
+    return result;
 }
 
-
 OFCondition IODMultiframeDimensionModule::DimensionIndexItem::setDimensionIndexPointer(const DcmTagKey& value,
                                                                                        const OFBool checkValue)
 {
-  (void)checkValue;
-  if (value == DCM_UndefinedTagKey)
-    return EC_IllegalParameter;
+    (void)checkValue;
+    if (value == DCM_UndefinedTagKey)
+        return EC_IllegalParameter;
 
-  DcmAttributeTag *elem = OFstatic_cast(DcmAttributeTag*, DcmItem::newDicomElement(DCM_DimensionIndexPointer));
-  if (elem == NULL)
-    return EC_InternalError;
+    DcmAttributeTag* elem = OFstatic_cast(DcmAttributeTag*, DcmItem::newDicomElement(DCM_DimensionIndexPointer));
+    if (elem == NULL)
+        return EC_InternalError;
 
-  OFCondition result;
-  Uint16 *attrTagArray;
-  result = elem->putTagVal(value);
-  if (result.good()) result = elem->getUint16Array(attrTagArray);
-  if (result.good()) result = m_Item->putAndInsertUint16Array(DCM_DimensionIndexPointer, attrTagArray, 1);
-  delete elem;
+    OFCondition result;
+    Uint16* attrTagArray;
+    result = elem->putTagVal(value);
+    if (result.good())
+        result = elem->getUint16Array(attrTagArray);
+    if (result.good())
+        result = m_Item->putAndInsertUint16Array(DCM_DimensionIndexPointer, attrTagArray, 1);
+    delete elem;
 
-  return result;
+    return result;
 }
 
-
 OFCondition IODMultiframeDimensionModule::DimensionIndexItem::setDimensionIndexPrivateCreator(const OFString& value,
-                                                                                                     const OFBool checkValue)
+                                                                                              const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_DimensionIndexPrivateCreator, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_DimensionIndexPrivateCreator, value);
+    return result;
 }
 
-
 OFCondition IODMultiframeDimensionModule::DimensionIndexItem::setDimensionOrganizationUID(const OFString& value,
-                                                                                                 const OFBool checkValue)
+                                                                                          const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_DimensionOrganizationUID, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_DimensionOrganizationUID, value);
+    return result;
 }
 
-
-
 // -- Dimension Organization Sequence Item --
 
 IODMultiframeDimensionModule::DimensionOrganizationItem::DimensionOrganizationItem(OFshared_ptr<DcmItem> data,
                                                                                    OFshared_ptr<IODRules> rules,
                                                                                    IODComponent* parent)
-: IODComponent(data, rules, parent)
+    : IODComponent(data, rules, parent)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
 IODMultiframeDimensionModule::DimensionOrganizationItem::DimensionOrganizationItem(IODComponent* parent)
-: IODComponent(parent)
+    : IODComponent(parent)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODMultiframeDimensionModule::DimensionOrganizationItem::~DimensionOrganizationItem()
 {
-  // Nothing to do
+    // Nothing to do
 }
 
-
 void IODMultiframeDimensionModule::DimensionOrganizationItem::resetRules()
 {
-  // Concatenation attributes
-  m_Rules->addRule(new IODRule(DCM_DimensionOrganizationUID, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    // Concatenation attributes
+    m_Rules->addRule(new IODRule(DCM_DimensionOrganizationUID, "1", "1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
 }
 
-
 OFString IODMultiframeDimensionModule::DimensionOrganizationItem::getName() const
 {
-  return "DimensionOrganizationSequence";
+    return "DimensionOrganizationSequence";
 }
 
-OFCondition IODMultiframeDimensionModule::DimensionOrganizationItem::getDimensionOrganizationUID(OFString& value,
-                                                                                                 const long signed int pos) const
+OFCondition
+IODMultiframeDimensionModule::DimensionOrganizationItem::getDimensionOrganizationUID(OFString& value,
+                                                                                     const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_DimensionOrganizationUID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_DimensionOrganizationUID, *m_Item, value, pos);
 }
 
-
-OFCondition IODMultiframeDimensionModule::DimensionOrganizationItem::setDimensionOrganizationUID(const OFString& value, const OFBool checkValue)
+OFCondition
+IODMultiframeDimensionModule::DimensionOrganizationItem::setDimensionOrganizationUID(const OFString& value,
+                                                                                     const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_DimensionOrganizationUID, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_DimensionOrganizationUID, value);
+    return result;
 }
index b706fb94c6fe2b902ad8b0eb328cdfc37ad4b066..fac6ec7c58e60c7f2fb34926f7aaa688aa6787df 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"
 #include "dcmtk/dcmiod/modmultiframefg.h"
-#include "dcmtk/dcmdata/dcvrtm.h"
+#include "dcmtk/config/osconfig.h"
 #include "dcmtk/dcmdata/dcvrda.h"
-#include "dcmtk/dcmdata/dcvrui.h"
 #include "dcmtk/dcmdata/dcvris.h"
+#include "dcmtk/dcmdata/dcvrtm.h"
+#include "dcmtk/dcmdata/dcvrui.h"
 #include "dcmtk/dcmiod/iodutil.h" // for static helpers
 
 const OFString IODMultiFrameFGModule::m_ModuleName = "MultiframeFunctionalGroupsModule";
 
-
-IODMultiFrameFGModule::IODMultiFrameFGModule(OFshared_ptr<DcmItem> data,
-                                             OFshared_ptr<IODRules> rules)
-: IODModule(data, rules),
-  m_ConcatenationInfo(data, rules)
+IODMultiFrameFGModule::IODMultiFrameFGModule(OFshared_ptr<DcmItem> data, OFshared_ptr<IODRules> rules)
+    : IODModule(data, rules)
+    , m_ConcatenationInfo(data, rules)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 OFString IODMultiFrameFGModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 IODMultiFrameFGModule::IODMultiFrameFGModule()
-: IODModule(),
-  m_ConcatenationInfo()
+    : IODModule()
+    , m_ConcatenationInfo()
 {
-  resetRules();
+    resetRules();
 }
 
-
 void IODMultiFrameFGModule::resetRules()
 {
-  m_Rules->addRule(new IODRule(DCM_InstanceNumber, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ContentDate, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ContentTime, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_NumberOfFrames, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_RepresentativeFrameNumber, "1", "3", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_ConcatenationInfo.resetRules();
+    m_Rules->addRule(new IODRule(DCM_InstanceNumber, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ContentDate, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ContentTime, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_NumberOfFrames, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_RepresentativeFrameNumber, "1", "3", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_ConcatenationInfo.resetRules();
 }
 
-
 IODMultiFrameFGModule::~IODMultiFrameFGModule()
 {
 }
 
-
-IODMultiFrameFGModule::ConcatenationInfo& IODMultiFrameFGModule::getConcatenationInfo()
+OFCondition IODMultiFrameFGModule::read(DcmItem& source, const bool clearOldData)
 {
-  return m_ConcatenationInfo;
+    IODModule::read(source, clearOldData);
+    m_ConcatenationInfo.read(source, clearOldData);
+    return EC_Normal;
 }
 
-
-OFCondition IODMultiFrameFGModule::getInstanceNumber(Sint32& value,
-                                                     const unsigned int pos)
+OFCondition IODMultiFrameFGModule::write(DcmItem& destination)
 {
-  return m_Item->findAndGetSint32(DCM_InstanceNumber, value, pos);
+    OFCondition result = IODModule::write(destination);
+    if (result.good())
+        m_ConcatenationInfo.write(destination);
+    return result;
 }
 
-
-OFCondition IODMultiFrameFGModule::getContentDate(OFString& value,
-                                                  const long signed int pos)
+IODMultiFrameFGModule::ConcatenationInfo& IODMultiFrameFGModule::getConcatenationInfo()
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_ContentDate, *m_Item, value, pos);
+    return m_ConcatenationInfo;
 }
 
-
-OFCondition IODMultiFrameFGModule::getContentTime(OFString& value,
-                                                  const long signed int pos)
+OFCondition IODMultiFrameFGModule::getInstanceNumber(Sint32& value, const unsigned int pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_ContentTime, *m_Item, value, pos);
+    return m_Item->findAndGetSint32(DCM_InstanceNumber, value, pos);
 }
 
-
-OFCondition IODMultiFrameFGModule::getNumberOfFrames(Sint32& value,
-                                                     const unsigned int pos)
+OFCondition IODMultiFrameFGModule::getContentDate(OFString& value, const long signed int pos)
 {
-  return m_Item->findAndGetSint32(DCM_NumberOfFrames, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_ContentDate, *m_Item, value, pos);
 }
 
+OFCondition IODMultiFrameFGModule::getContentTime(OFString& value, const long signed int pos)
+{
+    return DcmIODUtil::getStringValueFromItem(DCM_ContentTime, *m_Item, value, pos);
+}
 
-OFCondition IODMultiFrameFGModule::getRepresentativeFrameNumber(Uint16& value,
-                                                                const unsigned int pos)
+OFCondition IODMultiFrameFGModule::getNumberOfFrames(Sint32& value, const unsigned int pos)
 {
-  return m_Item->findAndGetUint16(DCM_RepresentativeFrameNumber, value, pos);
+    return m_Item->findAndGetSint32(DCM_NumberOfFrames, value, pos);
 }
 
+OFCondition IODMultiFrameFGModule::getRepresentativeFrameNumber(Uint16& value, const unsigned int pos)
+{
+    return m_Item->findAndGetUint16(DCM_RepresentativeFrameNumber, value, pos);
+}
 
 // -- setters --
 
-
-OFCondition IODMultiFrameFGModule::setConcatenationInfo(const IODMultiFrameFGModule::ConcatenationInfo& concatenationInfo)
+OFCondition
+IODMultiFrameFGModule::setConcatenationInfo(const IODMultiFrameFGModule::ConcatenationInfo& concatenationInfo)
 {
-  m_ConcatenationInfo = concatenationInfo;
-  return EC_Normal;
+    m_ConcatenationInfo = concatenationInfo;
+    return EC_Normal;
 }
 
-
-OFCondition IODMultiFrameFGModule::setInstanceNumber(const OFString& value,
-                                                     const OFBool checkValue)
+OFCondition IODMultiFrameFGModule::setInstanceNumber(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmIntegerString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_InstanceNumber, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmIntegerString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_InstanceNumber, value);
+    return result;
 }
 
-
-OFCondition IODMultiFrameFGModule::setContentDate(const OFString& value,
-                                                  const OFBool checkValue)
+OFCondition IODMultiFrameFGModule::setContentDate(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDate::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_ContentDate, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDate::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_ContentDate, value);
+    return result;
 }
 
-
-OFCondition IODMultiFrameFGModule::setContentTime(const OFString& value,
-                                                  const OFBool checkValue)
+OFCondition IODMultiFrameFGModule::setContentTime(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmTime::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = result = m_Item->putAndInsertOFStringArray(DCM_ContentTime, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmTime::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = result = m_Item->putAndInsertOFStringArray(DCM_ContentTime, value);
+    return result;
 }
 
-
 OFCondition IODMultiFrameFGModule::setNumberOfFrames(const Uint32 value)
 {
-  if (value > 2147483647)
-  {
-     DCMIOD_ERROR("Cannot set Number of Frames to " << value << ": Maximum permitted value is 2147483647");
-     return EC_InvalidValue;
-  }
-  OFCondition result;
-  OFStringStream oss;
-  oss << value;
-  OFSTRINGSTREAM_GETSTR(oss,tempstr);
-  result = m_Item->putAndInsertOFStringArray(DCM_NumberOfFrames, tempstr);
-  OFSTRINGSTREAM_FREESTR(tmpstr);
-  return result;
+    if (value > 2147483647)
+    {
+        DCMIOD_ERROR("Cannot set Number of Frames to " << value << ": Maximum permitted value is 2147483647");
+        return EC_InvalidValue;
+    }
+    OFCondition result;
+    OFStringStream oss;
+    oss << value;
+    OFSTRINGSTREAM_GETSTR(oss, tempstr);
+    result = m_Item->putAndInsertOFStringArray(DCM_NumberOfFrames, tempstr);
+    OFSTRINGSTREAM_FREESTR(tmpstr);
+    return result;
 }
 
-
 OFCondition IODMultiFrameFGModule::setRepresentativeFrameNumber(const Uint16 value)
 {
-  return m_Item->putAndInsertUint16(DCM_RepresentativeFrameNumber, value);
+    return m_Item->putAndInsertUint16(DCM_RepresentativeFrameNumber, value);
 }
 
-
-IODMultiFrameFGModule::ConcatenationInfo::ConcatenationInfo(OFshared_ptr<DcmItem> data,
-                                                            OFshared_ptr<IODRules> rules)
-: IODComponent(data, rules)
+IODMultiFrameFGModule::ConcatenationInfo::ConcatenationInfo(OFshared_ptr<DcmItem> data, OFshared_ptr<IODRules> rules)
+    : IODComponent(data, rules)
 {
 
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODMultiFrameFGModule::ConcatenationInfo::ConcatenationInfo(IODComponent* parent)
-: IODComponent(parent)
+    : IODComponent(parent)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODMultiFrameFGModule::ConcatenationInfo::~ConcatenationInfo()
 {
-  // Nothing to do
+    // Nothing to do
 }
 
-
 OFString IODMultiFrameFGModule::ConcatenationInfo::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 void IODMultiFrameFGModule::ConcatenationInfo::resetRules()
 {
-  // Concatenation attributes
-  m_Rules->addRule(new IODRule(DCM_ConcatenationFrameOffsetNumber, "1", "1C", m_ModuleName, DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ConcatenationUID, "1", "1C", m_ModuleName, DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_SOPInstanceUIDOfConcatenationSource, "1", "1C", m_ModuleName, DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_InConcatenationNumber, "1", "1C", m_ModuleName, DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_InConcatenationTotalNumber, "1", "3", m_ModuleName, DcmIODTypes::IE_INSTANCE), OFTrue);
+    // Concatenation attributes
+    m_Rules->addRule(new IODRule(DCM_ConcatenationFrameOffsetNumber, "1", "1C", m_ModuleName, DcmIODTypes::IE_INSTANCE),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ConcatenationUID, "1", "1C", m_ModuleName, DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(
+        new IODRule(DCM_SOPInstanceUIDOfConcatenationSource, "1", "1C", m_ModuleName, DcmIODTypes::IE_INSTANCE),
+        OFTrue);
+    m_Rules->addRule(new IODRule(DCM_InConcatenationNumber, "1", "1C", m_ModuleName, DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_InConcatenationTotalNumber, "1", "3", m_ModuleName, DcmIODTypes::IE_INSTANCE),
+                     OFTrue);
 }
 
-
 OFCondition IODMultiFrameFGModule::ConcatenationInfo::getConcatenationFrameOffsetNumber(Uint32& value,
-                                                                                       const unsigned int pos)
+                                                                                        const unsigned int pos)
 {
-  return m_Item->findAndGetUint32(DCM_ConcatenationFrameOffsetNumber, value, pos);
+    return m_Item->findAndGetUint32(DCM_ConcatenationFrameOffsetNumber, value, pos);
 }
 
-
-OFCondition IODMultiFrameFGModule::ConcatenationInfo::getConcatenationUID(OFString& value,
-                                                                          const signed long pos)
+OFCondition IODMultiFrameFGModule::ConcatenationInfo::getConcatenationUID(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_ConcatenationUID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_ConcatenationUID, *m_Item, value, pos);
 }
 
-
 OFCondition IODMultiFrameFGModule::ConcatenationInfo::getSOPInstanceUIDOfConcatenationSource(OFString& value,
                                                                                              const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_SOPInstanceUIDOfConcatenationSource, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_SOPInstanceUIDOfConcatenationSource, *m_Item, value, pos);
 }
 
-
-OFCondition IODMultiFrameFGModule::ConcatenationInfo::getInConcatenationNumber(Uint16& value,
-                                                                               const unsigned int pos)
+OFCondition IODMultiFrameFGModule::ConcatenationInfo::getInConcatenationNumber(Uint16& value, const unsigned int pos)
 {
-  return m_Item->findAndGetUint16(DCM_InConcatenationNumber, value, pos);
+    return m_Item->findAndGetUint16(DCM_InConcatenationNumber, value, pos);
 }
 
-
 OFCondition IODMultiFrameFGModule::ConcatenationInfo::getInConcatenationTotalNumber(Uint16& value,
                                                                                     const unsigned int pos)
 {
-  return m_Item->findAndGetUint16(DCM_InConcatenationTotalNumber, value, pos);
+    return m_Item->findAndGetUint16(DCM_InConcatenationTotalNumber, value, pos);
 }
 
-
 OFCondition IODMultiFrameFGModule::ConcatenationInfo::setConcatenationFrameOffsetNumber(const Uint32 value)
 {
-  return m_Item->putAndInsertUint32(DCM_ConcatenationFrameOffsetNumber, value);
+    return m_Item->putAndInsertUint32(DCM_ConcatenationFrameOffsetNumber, value);
 }
 
-
 OFCondition IODMultiFrameFGModule::ConcatenationInfo::setConcatenationUID(const OFString& value,
                                                                           const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_ConcatenationUID, value);
-  return result;
-
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_ConcatenationUID, value);
+    return result;
 }
 
-
 OFCondition IODMultiFrameFGModule::ConcatenationInfo::setSOPInstanceUIDOfConcatenationSource(const OFString& value,
                                                                                              const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_SOPInstanceUIDOfConcatenationSource, value);
-  return result;
-
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_SOPInstanceUIDOfConcatenationSource, value);
+    return result;
 }
 
-
 OFCondition IODMultiFrameFGModule::ConcatenationInfo::setInConcatenationNumber(const Uint16 value)
 {
-  return m_Item->putAndInsertUint16(DCM_InConcatenationNumber, value);
+    return m_Item->putAndInsertUint16(DCM_InConcatenationNumber, value);
 }
 
-
 OFCondition IODMultiFrameFGModule::ConcatenationInfo::setInConcatenationTotalNumber(const Uint16 value)
 {
-  return m_Item->putAndInsertUint16(DCM_InConcatenationTotalNumber, value);
+    return m_Item->putAndInsertUint16(DCM_InConcatenationTotalNumber, value);
 }
index 48013f5a82a4553da3f3fbcc5ffe670a862510d2..82152e92f8cac3d57922bf22f89199c563ec96f8 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modpatient.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/iodutil.h"
 
 const OFString IODPatientModule::m_ModuleName = "PatientModule";
 
-
-IODPatientModule::IODPatientModule(OFshared_ptr<DcmItem> item,
-                                   OFshared_ptr<IODRules> rules)
-: IODModule(item, rules)
+IODPatientModule::IODPatientModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODModule(item, rules)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 OFString IODPatientModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 IODPatientModule::IODPatientModule()
-: IODModule()
+    : IODModule()
 {
-  resetRules();
+    resetRules();
 }
 
-
 void IODPatientModule::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_PatientName, "1","2",getName(), DcmIODTypes::IE_PATIENT), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PatientID, "1","2", getName(), DcmIODTypes::IE_PATIENT), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PatientBirthDate, "1","2", getName(), DcmIODTypes::IE_PATIENT), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PatientSex, "1","2", getName(), DcmIODTypes::IE_PATIENT), OFTrue);
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_PatientName, "1", "2", getName(), DcmIODTypes::IE_PATIENT), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PatientID, "1", "2", getName(), DcmIODTypes::IE_PATIENT), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PatientBirthDate, "1", "2", getName(), DcmIODTypes::IE_PATIENT), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PatientSex, "1", "2", getName(), DcmIODTypes::IE_PATIENT), OFTrue);
 }
 
-
 IODPatientModule::~IODPatientModule()
 {
 }
 
-
 // --- get attributes (C++ string) ---
 
-
-OFCondition IODPatientModule::getPatientName(OFString &value,
-                                             const signed long pos) const
+OFCondition IODPatientModule::getPatientName(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_PatientName, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_PatientName, *m_Item, value, pos);
 }
 
-
-OFCondition IODPatientModule::getPatientBirthDate(OFString &value,
-                                                  const signed long pos) const
+OFCondition IODPatientModule::getPatientBirthDate(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_PatientBirthDate, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_PatientBirthDate, *m_Item, value, pos);
 }
 
-
-OFCondition IODPatientModule::getPatientSex(OFString &value,
-                                            const signed long pos) const
+OFCondition IODPatientModule::getPatientSex(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_PatientSex, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_PatientSex, *m_Item, value, pos);
 }
 
-OFCondition IODPatientModule::getPatientID(OFString &value,
-                                           const signed long pos) const
+OFCondition IODPatientModule::getPatientID(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_PatientID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_PatientID, *m_Item, value, pos);
 }
 
 // --- set attributes ---
 
-OFCondition IODPatientModule::setPatientName(const OFString &value,
-                                             const OFBool checkValue)
+OFCondition IODPatientModule::setPatientName(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmPersonName::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_PatientName, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmPersonName::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_PatientName, value);
+    return result;
 }
 
-
-OFCondition IODPatientModule::setPatientID(const OFString &value,
-                                           const OFBool checkValue)
+OFCondition IODPatientModule::setPatientID(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_PatientID, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_PatientID, value);
+    return result;
 }
 
-
-OFCondition IODPatientModule::setPatientBirthDate(const OFString &value,
-                                                  const OFBool checkValue)
+OFCondition IODPatientModule::setPatientBirthDate(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDate::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_PatientBirthDate, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDate::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_PatientBirthDate, value);
+    return result;
 }
 
-
-OFCondition IODPatientModule::setPatientSex(const OFString &value,
-                                            const OFBool checkValue)
+OFCondition IODPatientModule::setPatientSex(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_PatientSex, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_PatientSex, value);
+    return result;
 }
-
index d87b22c96d449421f9b5092db3d5452b2d2a456f..b7af015c61fb14936bff9544703de0b9928e2c9d 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modpatientstudy.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/iodutil.h"
 
 const OFString IODPatientStudyModule::m_ModuleName = "PatientStudyModule";
 
-
-IODPatientStudyModule::IODPatientStudyModule(OFshared_ptr<DcmItem> item,
-                                             OFshared_ptr<IODRules> rules)
-: IODModule(item, rules)
+IODPatientStudyModule::IODPatientStudyModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODModule(item, rules)
 {
-  resetRules();
+    resetRules();
 }
 
-
 OFString IODPatientStudyModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 IODPatientStudyModule::IODPatientStudyModule()
-: IODModule()
+    : IODModule()
 {
-  resetRules();
+    resetRules();
 }
 
-
 void IODPatientStudyModule::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_AdmittingDiagnosesDescription, "1-n","3",getName(), DcmIODTypes::IE_STUDY), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PatientAge, "1","3", getName(), DcmIODTypes::IE_STUDY), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PatientSize, "1","3", getName(), DcmIODTypes::IE_STUDY), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PatientWeight, "1","3", getName(), DcmIODTypes::IE_STUDY), OFTrue);
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_AdmittingDiagnosesDescription, "1-n", "3", getName(), DcmIODTypes::IE_STUDY),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PatientAge, "1", "3", getName(), DcmIODTypes::IE_STUDY), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PatientSize, "1", "3", getName(), DcmIODTypes::IE_STUDY), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PatientWeight, "1", "3", getName(), DcmIODTypes::IE_STUDY), OFTrue);
 }
 
-
 IODPatientStudyModule::~IODPatientStudyModule()
 {
 }
 
-
 // --- get attributes (C++ string) ---
 
-OFCondition IODPatientStudyModule::getAdmittingDiagnosesDescription(OFString& value,
-                                                                    const signed long pos) const
+OFCondition IODPatientStudyModule::getAdmittingDiagnosesDescription(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_AdmittingDiagnosesDescription, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_AdmittingDiagnosesDescription, *m_Item, value, pos);
 }
 
-
-OFCondition IODPatientStudyModule::getPatientAge(OFString& value,
-                                                 const signed long pos) const
+OFCondition IODPatientStudyModule::getPatientAge(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_PatientAge, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_PatientAge, *m_Item, value, pos);
 }
 
-
-OFCondition IODPatientStudyModule::getPatientWeight(Float64& value,
-                                                    const unsigned long pos) const
+OFCondition IODPatientStudyModule::getPatientWeight(Float64& value, const unsigned long pos) const
 {
-  return DcmIODUtil::getFloat64ValueFromItem(DCM_PatientWeight, *m_Item, value, pos);
+    return DcmIODUtil::getFloat64ValueFromItem(DCM_PatientWeight, *m_Item, value, pos);
 }
 
-
-OFCondition IODPatientStudyModule::getPatientSize(Float64& value,
-                                                  const unsigned long pos) const
+OFCondition IODPatientStudyModule::getPatientSize(Float64& value, const unsigned long pos) const
 {
-  return DcmIODUtil::getFloat64ValueFromItem(DCM_PatientSize, *m_Item, value, pos);
+    return DcmIODUtil::getFloat64ValueFromItem(DCM_PatientSize, *m_Item, value, pos);
 }
 
-
 // --- set attributes ---
 
-
-OFCondition IODPatientStudyModule::setAdmittingDiagnosesDescription(const OFString& value,
-                                                                    const OFBool checkValue)
+OFCondition IODPatientStudyModule::setAdmittingDiagnosesDescription(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1-n") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_AdmittingDiagnosesDescription, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1-n") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_AdmittingDiagnosesDescription, value);
+    return result;
 }
 
-OFCondition IODPatientStudyModule::setPatientAge(const OFString& value,
-                                                 const OFBool checkValue)
+OFCondition IODPatientStudyModule::setPatientAge(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmAgeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_PatientAge, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmAgeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_PatientAge, value);
+    return result;
 }
 
-
-OFCondition IODPatientStudyModule::setPatientSize(const OFString& value,
-                                                  const OFBool checkValue)
+OFCondition IODPatientStudyModule::setPatientSize(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_PatientSize, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_PatientSize, value);
+    return result;
 }
 
-
-OFCondition IODPatientStudyModule::setPatientWeight(const OFString& value,
-                                                    const OFBool checkValue)
+OFCondition IODPatientStudyModule::setPatientWeight(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_PatientWeight, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmDecimalString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_PatientWeight, value);
+    return result;
 }
index 4019fd11250edb00cf22da3a8c90682cbf0d5478..92b39b95c2d38b206327766687d1020fe4dac999 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modsegmentationseries.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/iodutil.h"
 
 const OFString IODSegmentationSeriesModule::m_ModuleName = "SegmentationSeriesModule";
 
-
-IODSegmentationSeriesModule::IODSegmentationSeriesModule(OFshared_ptr<DcmItem> item,
-                                                         OFshared_ptr<IODRules> rules)
-: IODModule(item, rules)
+IODSegmentationSeriesModule::IODSegmentationSeriesModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODModule(item, rules)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODSegmentationSeriesModule::IODSegmentationSeriesModule()
-: IODModule()
+    : IODModule()
 {
-  resetRules();
+    resetRules();
 }
 
-
 IODSegmentationSeriesModule::~IODSegmentationSeriesModule()
 {
 }
 
-
 OFString IODSegmentationSeriesModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 void IODSegmentationSeriesModule::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_Modality, "1","1", getName(), DcmIODTypes::IE_SERIES, "SEG"), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_SeriesNumber, "1","1", getName(), DcmIODTypes::IE_SERIES, "1"), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ReferencedSOPClassUID, "1","1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ReferencedSOPInstanceUID, "1","1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_Modality, "1", "1", getName(), DcmIODTypes::IE_SERIES, "SEG"), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_SeriesNumber, "1", "1", getName(), DcmIODTypes::IE_SERIES, "1"), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ReferencedSOPClassUID, "1", "1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ReferencedSOPInstanceUID, "1", "1C", getName(), DcmIODTypes::IE_SERIES), OFTrue);
 }
 
-
-OFCondition IODSegmentationSeriesModule::getModality(OFString &value,
-                                                     const signed long pos) const
+OFCondition IODSegmentationSeriesModule::getModality(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_Modality, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_Modality, *m_Item, value, pos);
 }
 
-
-OFCondition IODSegmentationSeriesModule::getSeriesNumber(OFString &value,
-                                                         const signed long pos) const
+OFCondition IODSegmentationSeriesModule::getSeriesNumber(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_SeriesNumber, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_SeriesNumber, *m_Item, value, pos);
 }
 
-
-OFCondition IODSegmentationSeriesModule::getPPSSOPClassUID(OFString &value,
-                                                           const signed long pos) const
+OFCondition IODSegmentationSeriesModule::getPPSSOPClassUID(OFString& value, const signed long pos) const
 {
-  DcmItem *localItem = NULL;
-  OFCondition result = m_Item->findAndGetSequenceItem(DCM_ReferencedPerformedProcedureStepSequence, localItem, 0);
-  if (result.good())
-  {
-    result = DcmIODUtil::getStringValueFromItem(DCM_ReferencedSOPClassUID, *localItem, value, pos);
-  }
-  return result;
+    DcmItem* localItem = NULL;
+    OFCondition result = m_Item->findAndGetSequenceItem(DCM_ReferencedPerformedProcedureStepSequence, localItem, 0);
+    if (result.good())
+    {
+        result = DcmIODUtil::getStringValueFromItem(DCM_ReferencedSOPClassUID, *localItem, value, pos);
+    }
+    return result;
 }
 
-
-OFCondition IODSegmentationSeriesModule::getPPSSOPInstanceUID(OFString &value,
-                                                              const signed long pos) const
+OFCondition IODSegmentationSeriesModule::getPPSSOPInstanceUID(OFString& value, const signed long pos) const
 {
-  DcmItem *localItem = NULL;
-  OFCondition result = m_Item->findAndGetSequenceItem(DCM_ReferencedPerformedProcedureStepSequence, localItem, 0);
-  if (result.good())
-  {
-    result = DcmIODUtil::getStringValueFromItem(DCM_ReferencedSOPInstanceUID, *localItem, value, pos);
-  }
-  return result;
+    DcmItem* localItem = NULL;
+    OFCondition result = m_Item->findAndGetSequenceItem(DCM_ReferencedPerformedProcedureStepSequence, localItem, 0);
+    if (result.good())
+    {
+        result = DcmIODUtil::getStringValueFromItem(DCM_ReferencedSOPInstanceUID, *localItem, value, pos);
+    }
+    return result;
 }
 
-
-OFCondition IODSegmentationSeriesModule::setSeriesNumber(const OFString &value,
-                                                         const OFBool checkValue)
+OFCondition IODSegmentationSeriesModule::setSeriesNumber(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmIntegerString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_SeriesNumber, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmIntegerString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_SeriesNumber, value);
+    return result;
 }
 
-
-OFCondition IODSegmentationSeriesModule::setPPSSOPClassUID(const OFString& value,
-                                                           const OFBool checkValue)
+OFCondition IODSegmentationSeriesModule::setPPSSOPClassUID(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-  {
-    DcmItem *localItem = NULL;
-    result = m_Item->findOrCreateSequenceItem(DCM_ReferencedPerformedProcedureStepSequence, localItem, 0);
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
     if (result.good())
     {
-      result = m_Item->putAndInsertOFStringArray(DCM_ReferencedSOPClassUID, value);
+        DcmItem* localItem = NULL;
+        result = m_Item->findOrCreateSequenceItem(DCM_ReferencedPerformedProcedureStepSequence, localItem, 0);
+        if (result.good())
+        {
+            result = m_Item->putAndInsertOFStringArray(DCM_ReferencedSOPClassUID, value);
+        }
     }
-  }
-  return result;
+    return result;
 }
 
-
-OFCondition IODSegmentationSeriesModule::setPPSSOPInstanceUID(const OFString& value,
-                                                              const OFBool checkValue)
+OFCondition IODSegmentationSeriesModule::setPPSSOPInstanceUID(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-  {
-    DcmItem *localItem = NULL;
-    result = m_Item->findOrCreateSequenceItem(DCM_ReferencedPerformedProcedureStepSequence, localItem, 0);
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
     if (result.good())
     {
-      result = m_Item->putAndInsertOFStringArray(DCM_ReferencedSOPInstanceUID, value);
+        DcmItem* localItem = NULL;
+        result = m_Item->findOrCreateSequenceItem(DCM_ReferencedPerformedProcedureStepSequence, localItem, 0);
+        if (result.good())
+        {
+            result = m_Item->putAndInsertOFStringArray(DCM_ReferencedSOPInstanceUID, value);
+        }
     }
-  }
-  return result;
+    return result;
 }
index 9ea9f0749f1356c2da6b3a993c4258ad06b76044..a521d15d9291296930ee67e06579605474ca41f5 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modsopcommon.h"
-#include "dcmtk/dcmdata/dcuid.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmdata/dcuid.h"
 #include "dcmtk/dcmdata/dcvrcs.h"
-#include "dcmtk/dcmdata/dcvrui.h"
 #include "dcmtk/dcmdata/dcvrda.h"
-#include "dcmtk/dcmdata/dcvrtm.h"
 #include "dcmtk/dcmdata/dcvrsh.h"
+#include "dcmtk/dcmdata/dcvrtm.h"
+#include "dcmtk/dcmdata/dcvrui.h"
 #include "dcmtk/dcmiod/iodutil.h"
 
 const OFString IODSOPCommonModule::m_ModuleName = "SOPCommonModule";
 
-
-IODSOPCommonModule::IODSOPCommonModule(OFshared_ptr<DcmItem> item,
-                                       OFshared_ptr<IODRules> rules)
-: IODModule(item, rules)
+IODSOPCommonModule::IODSOPCommonModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODModule(item, rules)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODSOPCommonModule::IODSOPCommonModule()
-: IODModule()
+    : IODModule()
 {
-  resetRules();
+    resetRules();
 }
 
-
 void IODSOPCommonModule::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_SOPClassUID, "1","1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_SOPInstanceUID, "1","1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_SpecificCharacterSet, "1-n","1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_InstanceCreationDate, "1","3", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_InstanceCreationTime, "1","3", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_InstanceCreatorUID, "1","3", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_TimezoneOffsetFromUTC, "1","3", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
-
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_SOPClassUID, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_SOPInstanceUID, "1", "1", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_SpecificCharacterSet, "1-n", "1C", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_InstanceCreationDate, "1", "3", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_InstanceCreationTime, "1", "3", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_InstanceCreatorUID, "1", "3", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_TimezoneOffsetFromUTC, "1", "3", getName(), DcmIODTypes::IE_INSTANCE), OFTrue);
 }
 
-
 OFString IODSOPCommonModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
-
 void IODSOPCommonModule::inventMissing()
 {
-  // SOP Instance UID
-  ensureInstanceUID();
+    // SOP Instance UID
+    ensureInstanceUID();
 
-  // All other attributes
-  IODComponent::inventMissing();
+    // All other attributes
+    IODComponent::inventMissing();
 }
 
-
 IODSOPCommonModule::~IODSOPCommonModule()
 {
 }
 
-
 void IODSOPCommonModule::ensureInstanceUID(const OFBool correctInvalid)
 {
-  OFString uidstr;
+    OFString uidstr;
 
-  /* create new sop instance UID if required */
-  if (getSOPInstanceUID(uidstr).bad() || uidstr.empty() )
-  {
-    setSOPInstanceUID(DcmIODUtil::createUID(0 /* Instance Level */));
-  }
-  else if (!uidstr.empty() && correctInvalid)
-  {
-    if (DcmUniqueIdentifier::checkStringValue(uidstr, "1").bad())
+    /* create new sop instance UID if required */
+    if (getSOPInstanceUID(uidstr).bad() || uidstr.empty())
+    {
+        setSOPInstanceUID(DcmIODUtil::createUID(0 /* Instance Level */));
+    }
+    else if (!uidstr.empty() && correctInvalid)
     {
-      setSOPInstanceUID(DcmIODUtil::createUID(0 /* Instance Level */));    }
-  }
+        if (DcmUniqueIdentifier::checkStringValue(uidstr, "1").bad())
+        {
+            setSOPInstanceUID(DcmIODUtil::createUID(0 /* Instance Level */));
+        }
+    }
 }
 
-
-
-OFCondition IODSOPCommonModule::getSpecificCharacterSet(OFString &value,
-                                                        const signed long pos) const
+OFCondition IODSOPCommonModule::getSpecificCharacterSet(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_SpecificCharacterSet, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_SpecificCharacterSet, *m_Item, value, pos);
 }
 
-
-OFCondition IODSOPCommonModule::getSOPInstanceUID(OFString &value,
-                                                  const signed long pos) const
+OFCondition IODSOPCommonModule::getSOPInstanceUID(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_SOPInstanceUID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_SOPInstanceUID, *m_Item, value, pos);
 }
 
-
-OFCondition IODSOPCommonModule::getSOPClassUID(OFString &value,
-                                               const signed long pos) const
+OFCondition IODSOPCommonModule::getSOPClassUID(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_SOPClassUID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_SOPClassUID, *m_Item, value, pos);
 }
 
-
-OFCondition IODSOPCommonModule::getInstanceCreationDate(OFString &value,
-                                                        const signed long pos) const
+OFCondition IODSOPCommonModule::getInstanceCreationDate(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_InstanceCreationDate, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_InstanceCreationDate, *m_Item, value, pos);
 }
 
-
-OFCondition IODSOPCommonModule::getInstanceCreationTime(OFString &value,
-                                                        const signed long pos) const
+OFCondition IODSOPCommonModule::getInstanceCreationTime(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_InstanceCreationTime, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_InstanceCreationTime, *m_Item, value, pos);
 }
 
-
-OFCondition IODSOPCommonModule::getInstanceCreatorUID(OFString &value,
-                                                      const signed long pos) const
+OFCondition IODSOPCommonModule::getInstanceCreatorUID(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_InstanceCreatorUID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_InstanceCreatorUID, *m_Item, value, pos);
 }
 
-
-OFCondition IODSOPCommonModule::getTimezoneOffsetFromUTC(OFString& value,
-                                                         const signed long pos) const
+OFCondition IODSOPCommonModule::getTimezoneOffsetFromUTC(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_TimezoneOffsetFromUTC, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_TimezoneOffsetFromUTC, *m_Item, value, pos);
 }
 
-
-
-OFCondition IODSOPCommonModule::setSpecificCharacterSet(const OFString &value,
-                                                        const OFBool checkValue)
+OFCondition IODSOPCommonModule::setSpecificCharacterSet(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1-n") : EC_Normal;
-  if (result.good())
-  {
-    result = m_Item->putAndInsertOFStringArray(DCM_SpecificCharacterSet, value);
-  }
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1-n") : EC_Normal;
+    if (result.good())
+    {
+        result = m_Item->putAndInsertOFStringArray(DCM_SpecificCharacterSet, value);
+    }
+    return result;
 }
 
-
-OFCondition IODSOPCommonModule::setSOPClassUID(const OFString &value,
-                                              const OFBool checkValue)
+OFCondition IODSOPCommonModule::setSOPClassUID(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-  {
-    result = m_Item->putAndInsertOFStringArray(DCM_SOPClassUID, value);
-  }
-  return result;
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+    {
+        result = m_Item->putAndInsertOFStringArray(DCM_SOPClassUID, value);
+    }
+    return result;
 }
 
-
-OFCondition IODSOPCommonModule::setSOPInstanceUID(const OFString &value,
-                                                  const OFBool checkValue)
+OFCondition IODSOPCommonModule::setSOPInstanceUID(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-  {
-    result = m_Item->putAndInsertOFStringArray(DCM_SOPInstanceUID, value);
-  }
-  return result;
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+    {
+        result = m_Item->putAndInsertOFStringArray(DCM_SOPInstanceUID, value);
+    }
+    return result;
 }
 
-
-OFCondition IODSOPCommonModule::setInstanceCreationDate(const OFString &value,
-                                                        const OFBool checkValue)
+OFCondition IODSOPCommonModule::setInstanceCreationDate(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmDate::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-  {
-    result = m_Item->putAndInsertOFStringArray(DCM_InstanceCreationDate, value);
-  }
-  return result;
+    OFCondition result = (checkValue) ? DcmDate::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+    {
+        result = m_Item->putAndInsertOFStringArray(DCM_InstanceCreationDate, value);
+    }
+    return result;
 }
 
-
-OFCondition IODSOPCommonModule::setInstanceCreationTime(const OFString &value,
-                                                        const OFBool checkValue)
+OFCondition IODSOPCommonModule::setInstanceCreationTime(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmTime::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-  {
-    result = m_Item->putAndInsertOFStringArray(DCM_InstanceCreationTime, value);
-  }
-  return result;
+    OFCondition result = (checkValue) ? DcmTime::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+    {
+        result = m_Item->putAndInsertOFStringArray(DCM_InstanceCreationTime, value);
+    }
+    return result;
 }
 
-
-OFCondition IODSOPCommonModule::setInstanceCreatorUID(const OFString &value,
-                                                      const OFBool checkValue)
+OFCondition IODSOPCommonModule::setInstanceCreatorUID(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-  {
-    result = m_Item->putAndInsertOFStringArray(DCM_InstanceCreatorUID, value);
-  }
-  return result;
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+    {
+        result = m_Item->putAndInsertOFStringArray(DCM_InstanceCreatorUID, value);
+    }
+    return result;
 }
 
-
-OFCondition IODSOPCommonModule::setTimeZoneOffsetFromUTC(const OFString& value,
-                                                         const OFBool checkValue) const
+OFCondition IODSOPCommonModule::setTimeZoneOffsetFromUTC(const OFString& value, const OFBool checkValue) const
 {
-  OFCondition result;
-  if (checkValue)
-  {
-    result = DcmShortString::checkStringValue(value, "1");
+    OFCondition result;
+    if (checkValue)
+    {
+        result = DcmShortString::checkStringValue(value, "1");
+        if (result.good())
+        {
+            if (value.length() != 5)
+                result = IOD_EC_InvalidElementValue;
+        }
+    }
     if (result.good())
     {
-      if (value.length() != 5) result = IOD_EC_InvalidElementValue;
+        result = m_Item->putAndInsertOFStringArray(DCM_TimezoneOffsetFromUTC, value);
     }
-  }
-  if (result.good())
-  {
-    result = m_Item->putAndInsertOFStringArray(DCM_TimezoneOffsetFromUTC, value);
-  }
-  return result;
+    return result;
 }
index 4d496e3b99541cc941ed9c48a03e4e270fecd3d0..ee0079162ff06db07a03e6ea5d1ff885d31a9e95 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
-#include "dcmtk/dcmiod/modsynchronisation.h"
-#include "dcmtk/ofstd/ofstream.h"
-#include "dcmtk/dcmdata/dcvrui.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+#include "dcmtk/dcmdata/dcdeftag.h"
 #include "dcmtk/dcmdata/dcvrcs.h"
 #include "dcmtk/dcmdata/dcvrlo.h"
 #include "dcmtk/dcmdata/dcvrsh.h"
-#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmdata/dcvrui.h"
 #include "dcmtk/dcmiod/iodutil.h"
-
+#include "dcmtk/dcmiod/modsynchronisation.h"
+#include "dcmtk/ofstd/ofstream.h"
 
 const OFString IODSynchronizationModule::m_ModuleName = "SynchronizationModule";
 
-
-IODSynchronizationModule::IODSynchronizationModule(OFshared_ptr<DcmItem> item,
-                                                   OFshared_ptr<IODRules> rules)
-: IODModule(item, rules)
+IODSynchronizationModule::IODSynchronizationModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODModule(item, rules)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODSynchronizationModule::IODSynchronizationModule()
-: IODModule()
+    : IODModule()
 {
-  resetRules();
+    resetRules();
 }
 
-
 void IODSynchronizationModule::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_SynchronizationFrameOfReferenceUID, "1","1", getName(), DcmIODTypes::IE_FOR), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_SynchronizationTrigger, "1","1", getName(), DcmIODTypes::IE_FOR), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_TriggerSourceOrType, "1","3", getName(), DcmIODTypes::IE_FOR), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_SynchronizationChannel, "2","1C", getName(), DcmIODTypes::IE_FOR), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_AcquisitionTimeSynchronized, "1","1", getName(), DcmIODTypes::IE_FOR), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_TimeSource, "1","3", getName(), DcmIODTypes::IE_FOR), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_TimeDistributionProtocol, "1","3", getName(), DcmIODTypes::IE_FOR), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_NTPSourceAddress, "1","3", getName(), DcmIODTypes::IE_FOR), OFTrue);
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_SynchronizationFrameOfReferenceUID, "1", "1", getName(), DcmIODTypes::IE_FOR),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_SynchronizationTrigger, "1", "1", getName(), DcmIODTypes::IE_FOR), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_TriggerSourceOrType, "1", "3", getName(), DcmIODTypes::IE_FOR), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_SynchronizationChannel, "2", "1C", getName(), DcmIODTypes::IE_FOR), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_AcquisitionTimeSynchronized, "1", "1", getName(), DcmIODTypes::IE_FOR), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_TimeSource, "1", "3", getName(), DcmIODTypes::IE_FOR), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_TimeDistributionProtocol, "1", "3", getName(), DcmIODTypes::IE_FOR), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_NTPSourceAddress, "1", "3", getName(), DcmIODTypes::IE_FOR), OFTrue);
 }
 
-
-
 OFString IODSynchronizationModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 IODSynchronizationModule::~IODSynchronizationModule()
 {
 }
 
-
 OFCondition IODSynchronizationModule::getSynchronizationFrameOfReferenceUID(OFString& value,
                                                                             const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_SynchronizationFrameOfReferenceUID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_SynchronizationFrameOfReferenceUID, *m_Item, value, pos);
 }
 
-
-
-OFCondition IODSynchronizationModule::getSynchronizationTrigger(OFString& value,
-                                                                const signed long pos) const
+OFCondition IODSynchronizationModule::getSynchronizationTrigger(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_SynchronizationTrigger, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_SynchronizationTrigger, *m_Item, value, pos);
 }
 
-
-OFCondition IODSynchronizationModule::getTriggerSourceOrType(OFString& value,
-                                                             const signed long pos) const
+OFCondition IODSynchronizationModule::getTriggerSourceOrType(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_TriggerSourceOrType, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_TriggerSourceOrType, *m_Item, value, pos);
 }
 
-
 OFCondition IODSynchronizationModule::getSynchronizationChannel(OFVector<Uint16>& value) const
 {
-  DcmElement *elem = NULL;
-  OFCondition result = m_Item->findAndGetElement(DCM_SynchronizationChannel, elem);
-  if (elem)
-  {
-    result = DcmIODUtil::getUint16ValuesFromElement(*elem, value);
-  }
-  return result;
+    DcmElement* elem   = NULL;
+    OFCondition result = m_Item->findAndGetElement(DCM_SynchronizationChannel, elem);
+    if (elem)
+    {
+        result = DcmIODUtil::getUint16ValuesFromElement(*elem, value);
+    }
+    return result;
 }
 
-
-OFCondition IODSynchronizationModule::getAcquisitionTimeSynchronized(OFString& value,
-                                                                     const signed long pos) const
+OFCondition IODSynchronizationModule::getAcquisitionTimeSynchronized(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_AcquisitionTimeSynchronized, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_AcquisitionTimeSynchronized, *m_Item, value, pos);
 }
 
-
-OFCondition IODSynchronizationModule::getTimeSource(OFString& value,
-                                                    const signed long pos) const
+OFCondition IODSynchronizationModule::getTimeSource(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_TimeSource, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_TimeSource, *m_Item, value, pos);
 }
 
-
-OFCondition IODSynchronizationModule::getTimeDistributionProtocol(OFString& value,
-                                                                  const signed long pos) const
+OFCondition IODSynchronizationModule::getTimeDistributionProtocol(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_TimeDistributionProtocol, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_TimeDistributionProtocol, *m_Item, value, pos);
 }
 
-
-OFCondition IODSynchronizationModule::getNTPSourceAddress(OFString& value,
-                                                          const signed long pos) const
+OFCondition IODSynchronizationModule::getNTPSourceAddress(OFString& value, const signed long pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_NTPSourceAddress, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_NTPSourceAddress, *m_Item, value, pos);
 }
 
-
-OFCondition IODSynchronizationModule::setSynchronizationFrameofReferenceUID(const OFString &value,
+OFCondition IODSynchronizationModule::setSynchronizationFrameofReferenceUID(const OFString& value,
                                                                             const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_SynchronizationFrameOfReferenceUID, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_SynchronizationFrameOfReferenceUID, value);
+    return result;
 }
 
-
-OFCondition IODSynchronizationModule::setSynchronizationTrigger(const OFString &value,
-                                                                const OFBool checkValue)
+OFCondition IODSynchronizationModule::setSynchronizationTrigger(const OFString& value, const OFBool checkValue)
 {
-  if (checkValue && !isValidSynchronizationTrigger(value))
-  {
-    DCMIOD_ERROR("Synchronization Trigger does not allow value " << value << " (enumerated values)");
-    return IOD_EC_InvalidElementValue;
-  }
-  return m_Item->putAndInsertOFStringArray(DCM_SynchronizationTrigger, value);
+    if (checkValue && !isValidSynchronizationTrigger(value))
+    {
+        DCMIOD_ERROR("Synchronization Trigger does not allow value " << value << " (enumerated values)");
+        return IOD_EC_InvalidElementValue;
+    }
+    return m_Item->putAndInsertOFStringArray(DCM_SynchronizationTrigger, value);
 }
 
-
-OFCondition IODSynchronizationModule::setTriggerSourceOrType(const OFString &value,
-                                                             const OFBool checkValue)
+OFCondition IODSynchronizationModule::setTriggerSourceOrType(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_TriggerSourceOrType, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_TriggerSourceOrType, value);
+    return result;
 }
 
-
-OFCondition IODSynchronizationModule::setSynchronizationChannel(const OFPair<Uint16, Uint16> &value,
+OFCondition IODSynchronizationModule::setSynchronizationChannel(const OFPair<Uint16, Uint16>& value,
                                                                 const OFBool checkValue)
 {
-  (void)checkValue;
-  OFCondition result = m_Item->putAndInsertUint16(DCM_SynchronizationChannel, value.first, 0);
-  if (result.good())
-  {
-    result = m_Item->putAndInsertUint16(DCM_SynchronizationChannel, value.second, 0);
-  }
-  return result;
+    (void)checkValue;
+    OFCondition result = m_Item->putAndInsertUint16(DCM_SynchronizationChannel, value.first, 0);
+    if (result.good())
+    {
+        result = m_Item->putAndInsertUint16(DCM_SynchronizationChannel, value.second, 0);
+    }
+    return result;
 }
 
-
-OFCondition IODSynchronizationModule::setAcquisitionTimeSynchronized(const OFString &value,
-                                                                     const OFBool checkValue)
+OFCondition IODSynchronizationModule::setAcquisitionTimeSynchronized(const OFString& value, const OFBool checkValue)
 {
-  if (checkValue && !isValidAcquisitionTimeSynchronized(value))
-  {
-    DCMIOD_ERROR("Acquisition Time Synchronized must only allows values 'Y' and 'N' (enumerated values)");
-    return IOD_EC_InvalidElementValue;
-  }
-  return m_Item->putAndInsertOFStringArray(DCM_AcquisitionTimeSynchronized, value);
+    if (checkValue && !isValidAcquisitionTimeSynchronized(value))
+    {
+        DCMIOD_ERROR("Acquisition Time Synchronized must only allows values 'Y' and 'N' (enumerated values)");
+        return IOD_EC_InvalidElementValue;
+    }
+    return m_Item->putAndInsertOFStringArray(DCM_AcquisitionTimeSynchronized, value);
 }
 
-
-OFCondition IODSynchronizationModule::setTimeSource(const OFString &value,
-                                                    const OFBool checkValue)
+OFCondition IODSynchronizationModule::setTimeSource(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_TimeSource, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmShortString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_TimeSource, value);
+    return result;
 }
 
-
-OFCondition IODSynchronizationModule::setTimeDistributionProtocol(const OFString &value,
-                                                                  const OFBool checkValue)
+OFCondition IODSynchronizationModule::setTimeDistributionProtocol(const OFString& value, const OFBool checkValue)
 {
-  if (checkValue && !isValidTimeDistributionProtocol(value))
-  {
-    DCMIOD_ERROR("Time Distribution Protocol does not allow value " << value << " (enumerated values)");
-    return IOD_EC_InvalidElementValue;
-  }
-  return m_Item->putAndInsertOFStringArray(DCM_TimeDistributionProtocol, value);
+    if (checkValue && !isValidTimeDistributionProtocol(value))
+    {
+        DCMIOD_ERROR("Time Distribution Protocol does not allow value " << value << " (enumerated values)");
+        return IOD_EC_InvalidElementValue;
+    }
+    return m_Item->putAndInsertOFStringArray(DCM_TimeDistributionProtocol, value);
 }
 
-
-
-OFCondition IODSynchronizationModule::setNTPSourceAddress(const OFString &value,
-                                                          const OFBool checkValue)
+OFCondition IODSynchronizationModule::setNTPSourceAddress(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_NTPSourceAddress, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_NTPSourceAddress, value);
+    return result;
 }
 
-
-
 OFBool IODSynchronizationModule::isValidAcquisitionTimeSynchronized(const OFString& value)
 {
-  return ( (value == "Y") || (value == "N") );
-
+    return ((value == "Y") || (value == "N"));
 }
 
-
 OFBool IODSynchronizationModule::isValidTimeDistributionProtocol(const OFString& value)
 {
-  return ( (value == "NTP") || (value == "IRIG") || (value == "GPS") || (value == "SNTP") || (value == "PTP") );
+    return ((value == "NTP") || (value == "IRIG") || (value == "GPS") || (value == "SNTP") || (value == "PTP"));
 }
 
-
 OFBool IODSynchronizationModule::isValidSynchronizationTrigger(const OFString& value)
 {
-  return ( (value == "SOURCE") || (value == "EXTERNAL") || (value == "PASSTHRU") || (value == "NO TRIGGER") );
+    return ((value == "SOURCE") || (value == "EXTERNAL") || (value == "PASSTHRU") || (value == "NO TRIGGER"));
 }
-
index 9058d5d6a5fbaca3330832f6c679f372521fe925..3961ea5cb874d99641a81f2de331161c905195fb 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2017, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
 #include "dcmtk/dcmiod/modusfor.h"
-#include "dcmtk/ofstd/ofstream.h"
-#include "dcmtk/dcmdata/dcvrui.h"
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+#include "dcmtk/dcmdata/dcdeftag.h"
 #include "dcmtk/dcmdata/dcvrcs.h"
 #include "dcmtk/dcmdata/dcvrfd.h"
-#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmdata/dcvrui.h"
 #include "dcmtk/dcmiod/iodutil.h"
-
+#include "dcmtk/ofstd/ofstream.h"
 
 const OFString IODUSFoRModule::m_ModuleName = "UltrasoundFrameOfReferenceModule";
 
-
-IODUSFoRModule::IODUSFoRModule(OFshared_ptr<DcmItem> item,
-                                OFshared_ptr<IODRules> rules)
-: IODModule(item, rules)
+IODUSFoRModule::IODUSFoRModule(OFshared_ptr<DcmItem> item, OFshared_ptr<IODRules> rules)
+    : IODModule(item, rules)
 {
-  // reset element rules
-  resetRules();
+    // reset element rules
+    resetRules();
 }
 
-
 IODUSFoRModule::IODUSFoRModule()
-: IODModule()
+    : IODModule()
 {
-  resetRules();
+    resetRules();
 }
 
-
 void IODUSFoRModule::resetRules()
 {
-  // parameters are tag, VM, type. Overwrite old rules if any.
-  m_Rules->addRule(new IODRule(DCM_VolumeFrameOfReferenceUID, "1","1", getName(), DcmIODTypes::IE_FOR), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_UltrasoundAcquisitionGeometry, "1","1", getName(), DcmIODTypes::IE_FOR), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_ApexPosition, "3","1C", getName(), DcmIODTypes::IE_FOR), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_VolumeToTransducerRelationship, "1","1C", getName(), DcmIODTypes::IE_FOR), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_VolumeToTransducerMappingMatrix, "16","1", getName(), DcmIODTypes::IE_FOR), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_PatientFrameOfReferenceSource, "1","1C", getName(), DcmIODTypes::IE_FOR), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_TableFrameOfReferenceUID, "1","1C", getName(), DcmIODTypes::IE_FOR), OFTrue);
-  m_Rules->addRule(new IODRule(DCM_VolumeToTableMappingMatrix, "16","1C", getName(), DcmIODTypes::IE_FOR), OFTrue);
+    // parameters are tag, VM, type. Overwrite old rules if any.
+    m_Rules->addRule(new IODRule(DCM_VolumeFrameOfReferenceUID, "1", "1", getName(), DcmIODTypes::IE_FOR), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_UltrasoundAcquisitionGeometry, "1", "1", getName(), DcmIODTypes::IE_FOR), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_ApexPosition, "3", "1C", getName(), DcmIODTypes::IE_FOR), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_VolumeToTransducerRelationship, "1", "1C", getName(), DcmIODTypes::IE_FOR),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_VolumeToTransducerMappingMatrix, "16", "1", getName(), DcmIODTypes::IE_FOR),
+                     OFTrue);
+    m_Rules->addRule(new IODRule(DCM_PatientFrameOfReferenceSource, "1", "1C", getName(), DcmIODTypes::IE_FOR), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_TableFrameOfReferenceUID, "1", "1C", getName(), DcmIODTypes::IE_FOR), OFTrue);
+    m_Rules->addRule(new IODRule(DCM_VolumeToTableMappingMatrix, "16", "1C", getName(), DcmIODTypes::IE_FOR), OFTrue);
 }
 
-
 OFString IODUSFoRModule::getName() const
 {
-  return m_ModuleName;
+    return m_ModuleName;
 }
 
-
 IODUSFoRModule::~IODUSFoRModule()
 {
-  // Nothing to do
+    // Nothing to do
 }
 
-
-OFCondition IODUSFoRModule::getVolumeFrameOfReferenceUID(OFString& value,
-                                                         const long signed int pos) const
+OFCondition IODUSFoRModule::getVolumeFrameOfReferenceUID(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_VolumeFrameOfReferenceUID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_VolumeFrameOfReferenceUID, *m_Item, value, pos);
 }
 
-
-OFCondition IODUSFoRModule::getUltrasoundAcquisitionGeometry(OFString& value,
-                                                             const long signed int pos) const
+OFCondition IODUSFoRModule::getUltrasoundAcquisitionGeometry(OFString& value, const long signed int pos) const
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_UltrasoundAcquisitionGeometry, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_UltrasoundAcquisitionGeometry, *m_Item, value, pos);
 }
 
-
 OFCondition IODUSFoRModule::getApexPosition(OFVector<Float64>& value)
 {
-  return DcmIODUtil::getFloat64ValuesFromItem(DCM_ApexPosition, *m_Item, value);
+    return DcmIODUtil::getFloat64ValuesFromItem(DCM_ApexPosition, *m_Item, value);
 }
 
-
-OFCondition IODUSFoRModule::getApexPosition(Float64& value,
-                                            const long unsigned int pos) const
+OFCondition IODUSFoRModule::getApexPosition(Float64& value, const unsigned long pos) const
 {
-  return DcmIODUtil::getFloat64ValueFromItem(DCM_ApexPosition, *m_Item, value, pos);
+    return DcmIODUtil::getFloat64ValueFromItem(DCM_ApexPosition, *m_Item, value, pos);
 }
 
-
-OFCondition IODUSFoRModule::getVolumetoTransducerRelationship(OFString& value,
-                                                              const long signed int pos)
+OFCondition IODUSFoRModule::getVolumetoTransducerRelationship(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_UltrasoundAcquisitionGeometry, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_UltrasoundAcquisitionGeometry, *m_Item, value, pos);
 }
 
-
-OFCondition IODUSFoRModule::getVolumetoTransducerMappingMatrix(Float64& value,
-                                                               const signed long pos) const
+OFCondition IODUSFoRModule::getVolumetoTransducerMappingMatrix(Float64& value, const unsigned long pos) const
 {
-  return DcmIODUtil::getFloat64ValueFromItem(DCM_VolumeToTransducerMappingMatrix, *m_Item, value, pos);
+    return DcmIODUtil::getFloat64ValueFromItem(DCM_VolumeToTransducerMappingMatrix, *m_Item, value, pos);
 }
 
-
-OFCondition IODUSFoRModule::getVolumetoTransducerMappingMatrix(OFVector< Float64 >& value)
+OFCondition IODUSFoRModule::getVolumetoTransducerMappingMatrix(OFVector<Float64>& value)
 {
-  return DcmIODUtil::getFloat64ValuesFromItem(DCM_VolumeToTransducerMappingMatrix, *m_Item, value);
+    return DcmIODUtil::getFloat64ValuesFromItem(DCM_VolumeToTransducerMappingMatrix, *m_Item, value);
 }
 
-
-OFCondition IODUSFoRModule::getPatientFrameofReferenceSource(OFString& value,
-                                                             const long signed int pos)
+OFCondition IODUSFoRModule::getPatientFrameofReferenceSource(OFString& value, const long signed int pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_PatientFrameOfReferenceSource, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_PatientFrameOfReferenceSource, *m_Item, value, pos);
 }
 
-
-OFCondition IODUSFoRModule::getTableFrameofReferenceUID(OFString& value,
-                                                        const long signed int pos)
+OFCondition IODUSFoRModule::getTableFrameofReferenceUID(OFString& value, const long signed int pos)
 {
-  return DcmIODUtil::getStringValueFromItem(DCM_TableFrameOfReferenceUID, *m_Item, value, pos);
+    return DcmIODUtil::getStringValueFromItem(DCM_TableFrameOfReferenceUID, *m_Item, value, pos);
 }
 
-
-OFCondition IODUSFoRModule::getVolumetoTableMappingMatrix(Float64& value,
-                                                          const long signed int pos) const
+OFCondition IODUSFoRModule::getVolumetoTableMappingMatrix(Float64& value, const unsigned long pos) const
 {
-  return DcmIODUtil::getFloat64ValueFromItem(DCM_VolumeToTableMappingMatrix, *m_Item, value, pos);
+    return DcmIODUtil::getFloat64ValueFromItem(DCM_VolumeToTableMappingMatrix, *m_Item, value, pos);
 }
 
-
-OFCondition IODUSFoRModule::getVolumetoTableMappingMatrix(OFVector< Float64 >& value)
+OFCondition IODUSFoRModule::getVolumetoTableMappingMatrix(OFVector<Float64>& value)
 {
-  return DcmIODUtil::getFloat64ValuesFromItem(DCM_VolumeToTableMappingMatrix, *m_Item, value);
+    return DcmIODUtil::getFloat64ValuesFromItem(DCM_VolumeToTableMappingMatrix, *m_Item, value);
 }
 
-
-OFCondition IODUSFoRModule::setVolumeFrameOfReferenceUID(const OFString& value,
-                                                         const OFBool checkValue)
+OFCondition IODUSFoRModule::setVolumeFrameOfReferenceUID(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_VolumeFrameOfReferenceUID, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_VolumeFrameOfReferenceUID, value);
+    return result;
 }
 
-
-OFCondition IODUSFoRModule::setUltrasoundAcquisitionGeometry(const OFString& value,
-                                                             const OFBool checkValue)
+OFCondition IODUSFoRModule::setUltrasoundAcquisitionGeometry(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_UltrasoundAcquisitionGeometry, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_UltrasoundAcquisitionGeometry, value);
+    return result;
 }
 
-
-OFCondition IODUSFoRModule::setApexPosition(const Float64& xValue,
-                                            const Float64& yValue,
-                                            const Float64& zValue,
-                                            const OFBool)
+OFCondition
+IODUSFoRModule::setApexPosition(const Float64& xValue, const Float64& yValue, const Float64& zValue, const OFBool)
 {
 
-  DcmElement *elem = DcmItem::newDicomElement(DCM_ApexPosition);
-
+    DcmElement* elem = DcmItem::newDicomElement(DCM_ApexPosition);
 
-  OFCondition result = elem->putFloat64(xValue, 0);
-  if (result.good()) result = elem->putFloat64(yValue, 1);
-  if (result.good()) result = elem->putFloat64(zValue, 2);
-  m_Item->insert(elem);
+    OFCondition result = elem->putFloat64(xValue, 0);
+    if (result.good())
+        result = elem->putFloat64(yValue, 1);
+    if (result.good())
+        result = elem->putFloat64(zValue, 2);
+    m_Item->insert(elem);
 
-  return result;
+    return result;
 }
 
-
-OFCondition IODUSFoRModule::setVolumetoTransducerRelationship(const OFString& value,
-                                                              const OFBool checkValue)
+OFCondition IODUSFoRModule::setVolumetoTransducerRelationship(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_VolumeToTransducerRelationship, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_VolumeToTransducerRelationship, value);
+    return result;
 }
 
-
-OFCondition IODUSFoRModule::setVolumetoTransducerMappingMatrix(const OFVector< Float64 >& value,
-                                                               const OFBool checkValue)
+OFCondition IODUSFoRModule::setVolumetoTransducerMappingMatrix(const OFVector<Float64>& value, const OFBool checkValue)
 {
-  size_t vm = value.size();
-  if ( checkValue && (vm != 16) )
-  {
-    return EC_ValueMultiplicityViolated;
-  }
-
-  OFCondition result;
-
-  DcmElement* elem = NULL;
-  result = DcmItem::newDicomElement(elem, DCM_VolumeToTransducerMappingMatrix);
-  if (result.good())
-  {
-    for (size_t n = 0; result.good() && n < vm; n++)
+    size_t vm = value.size();
+    if (checkValue && (vm != 16))
     {
-      result = elem->putFloat64(value[n], OFstatic_cast(unsigned long, n));
+        return EC_ValueMultiplicityViolated;
     }
-  }
-  if (result.good())
-  {
-    result = m_Item->insert(elem);
-    if (result.bad()) delete elem;
-  }
-  return result;
-}
 
+    OFCondition result;
 
-OFCondition IODUSFoRModule::setPatientFrameOfReferenceSource(const OFString& value,
-                                                             const OFBool checkValue)
-{
-  OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_PatientFrameOfReferenceSource, value);
-  return result;
+    DcmElement* elem = NULL;
+    result           = DcmItem::newDicomElement(elem, DCM_VolumeToTransducerMappingMatrix);
+    if (result.good())
+    {
+        for (size_t n = 0; result.good() && n < vm; n++)
+        {
+            result = elem->putFloat64(value[n], OFstatic_cast(unsigned long, n));
+        }
+    }
+    if (result.good())
+    {
+        result = m_Item->insert(elem);
+        if (result.bad())
+            delete elem;
+    }
+    return result;
 }
 
-
-OFCondition IODUSFoRModule::setTableFrameofReferenceUID(const OFString& value,
-                                                        const OFBool checkValue)
+OFCondition IODUSFoRModule::setPatientFrameOfReferenceSource(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_Item->putAndInsertOFStringArray(DCM_TableFrameOfReferenceUID, value);
-  return result;
+    OFCondition result = (checkValue) ? DcmCodeString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_PatientFrameOfReferenceSource, value);
+    return result;
 }
 
+OFCondition IODUSFoRModule::setTableFrameofReferenceUID(const OFString& value, const OFBool checkValue)
+{
+    OFCondition result = (checkValue) ? DcmUniqueIdentifier::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_Item->putAndInsertOFStringArray(DCM_TableFrameOfReferenceUID, value);
+    return result;
+}
 
-OFCondition IODUSFoRModule::setVolumeToTableMappingMatrix(const OFVector< Float64 >& value,
-                                                          const OFBool checkValue)
+OFCondition IODUSFoRModule::setVolumeToTableMappingMatrix(const OFVector<Float64>& value, const OFBool checkValue)
 {
-  size_t vm = value.size();
-  if ( checkValue && (vm != 16) )
-  {
-    return EC_ValueMultiplicityViolated;
-  }
-
-  OFCondition result;
-
-  DcmElement* elem = NULL;
-  result = DcmItem::newDicomElement(elem, DCM_VolumeToTableMappingMatrix);
-  if (result.good())
-  {
-    for (size_t n = 0; result.good() && (n < vm); n++)
+    size_t vm = value.size();
+    if (checkValue && (vm != 16))
+    {
+        return EC_ValueMultiplicityViolated;
+    }
+
+    OFCondition result;
+
+    DcmElement* elem = NULL;
+    result           = DcmItem::newDicomElement(elem, DCM_VolumeToTableMappingMatrix);
+    if (result.good())
+    {
+        for (size_t n = 0; result.good() && (n < vm); n++)
+        {
+            result = elem->putFloat64(value[n], OFstatic_cast(unsigned long, n));
+        }
+    }
+    if (result.good())
     {
-      result = elem->putFloat64(value[n], OFstatic_cast(unsigned long, n));
+        result = m_Item->insert(elem);
+        if (result.bad())
+            delete elem;
     }
-  }
-  if (result.good())
-  {
-    result = m_Item->insert(elem);
-    if (result.bad()) delete elem;
-  }
-  return result;
+    return result;
 }
index 1ebae734342579536a3ccd089f2364e2758f03d8..b81014fae46188dce0515cd12348d7fb8e13fbb7 100644 (file)
@@ -1,5 +1,5 @@
 # declare executables
-DCMTK_ADD_EXECUTABLE(dcmiod_tests tests tcielabutil timagepixel)
+DCMTK_ADD_EXECUTABLE(dcmiod_tests tests tcielabutil tcodes timagepixel)
 
 # make sure executables are linked to the corresponding libraries
 DCMTK_TARGET_LINK_MODULES(dcmiod_tests dcmiod dcmdata oflog ofstd)
index e1438836d3e09082172f8d7f82733ed497bb1794..bcde22597cbe295cd43a79bb68b40d2a3cd3aa30 100644 (file)
@@ -1,13 +1,15 @@
 tcielabutil.o: tcielabutil.cc \
  ../../config/include/dcmtk/config/osconfig.h \
- ../../ofstd/include/dcmtk/ofstd/oftest.h \
- ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../include/dcmtk/dcmiod/cielabutil.h ../include/dcmtk/dcmiod/ioddef.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofrand.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
  ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
  ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
  ../../ofstd/include/dcmtk/ofstd/oftraits.h \
@@ -47,9 +49,130 @@ tcielabutil.o: tcielabutil.cc \
  ../../oflog/include/dcmtk/oflog/spi/logfact.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h
+tcodes.o: tcodes.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../ofstd/include/dcmtk/ofstd/ofrand.h \
- ../include/dcmtk/dcmiod/cielabutil.h ../include/dcmtk/dcmiod/ioddef.h
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmiod/iodrules.h ../include/dcmtk/dcmiod/iodtypes.h \
+ ../include/dcmtk/dcmiod/ioddef.h ../include/dcmtk/dcmiod/modbase.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h
 tests.o: tests.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/oftest.h \
  ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
@@ -101,30 +224,18 @@ tests.o: tests.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h
 timagepixel.o: timagepixel.cc \
  ../../config/include/dcmtk/config/osconfig.h \
- ../../ofstd/include/dcmtk/ofstd/oftest.h \
- ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../include/dcmtk/dcmiod/iodimage.h ../include/dcmtk/dcmiod/iodcommn.h \
+ ../include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
- ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
- ../../ofstd/include/dcmtk/ofstd/ofexit.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/ioddef.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
@@ -138,6 +249,7 @@ timagepixel.o: timagepixel.cc \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
  ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
@@ -149,22 +261,10 @@ timagepixel.o: timagepixel.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../include/dcmtk/dcmiod/iodimage.h \
- ../../ofstd/include/dcmtk/ofstd/ofvriant.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/variant.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/helpers.h \
- ../../ofstd/include/dcmtk/ofstd/ofalign.h \
- ../../ofstd/include/dcmtk/ofstd/ofdiag.h \
- ../../ofstd/include/dcmtk/ofstd/diag/push.def \
- ../../ofstd/include/dcmtk/ofstd/diag/cnvrsn.def \
- ../../ofstd/include/dcmtk/ofstd/diag/vsprfw.def \
- ../../ofstd/include/dcmtk/ofstd/diag/pop.def \
- ../include/dcmtk/dcmiod/iodcommn.h ../include/dcmtk/dcmiod/iodrules.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
- ../include/dcmtk/dcmiod/iodtypes.h ../include/dcmtk/dcmiod/ioddef.h \
- ../include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmiod/modpatient.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../include/dcmtk/dcmiod/modcommoninstanceref.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
@@ -172,8 +272,15 @@ timagepixel.o: timagepixel.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
@@ -234,18 +341,32 @@ timagepixel.o: timagepixel.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmiod/modbase.h \
+ ../include/dcmtk/dcmiod/iodmacro.h ../include/dcmtk/dcmiod/modbase.h \
+ ../include/dcmtk/dcmiod/iodreferences.h \
+ ../include/dcmtk/dcmiod/modequipment.h ../include/dcmtk/dcmiod/modfor.h \
+ ../include/dcmtk/dcmiod/modgeneralseries.h \
+ ../include/dcmtk/dcmiod/modgeneralstudy.h \
+ ../include/dcmtk/dcmiod/modpatient.h \
  ../include/dcmtk/dcmiod/modpatientstudy.h \
  ../../ofstd/include/dcmtk/ofstd/ofoption.h \
- ../include/dcmtk/dcmiod/modgeneralstudy.h \
- ../include/dcmtk/dcmiod/iodmacro.h \
- ../include/dcmtk/dcmiod/modequipment.h \
- ../include/dcmtk/dcmiod/modgeneralseries.h \
- ../include/dcmtk/dcmiod/modfor.h ../include/dcmtk/dcmiod/modsopcommon.h \
- ../include/dcmtk/dcmiod/modcommoninstanceref.h \
- ../include/dcmtk/dcmiod/iodreferences.h \
+ ../../ofstd/include/dcmtk/ofstd/ofalign.h \
+ ../include/dcmtk/dcmiod/modsopcommon.h \
  ../include/dcmtk/dcmiod/modgeneralimage.h \
  ../include/dcmtk/dcmiod/modimagepixelvariant.h \
  ../include/dcmtk/dcmiod/modimagepixelbase.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvriant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/variant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/helpers.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdiag.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/push.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/cnvrsn.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/vsprfw.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/pop.def \
+ ../include/dcmtk/dcmiod/modfloatingpointimagepixel.h \
  ../include/dcmtk/dcmiod/modimagepixel.h \
- ../include/dcmtk/dcmiod/modfloatingpointimagepixel.h
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h
index 4b8699bb5ad42e6457afaa5e6ff9b7cb7c7ac109..05d44501d3f037997c86bbfaf31590f7bdb4cfcb 100644 (file)
@@ -24,7 +24,7 @@ LIBDIRS = -L$(top_srcdir)/libsrc -L$(dcmioddir)/libsrc -L$(dcmdatadir)/libsrc \
 LOCALLIBS = -ldcmiod -ldcmdata -loflog -lofstd \
        $(TIFFLIBS) $(PNGLIBS) $(ZLIBLIBS) $(CHARCONVLIBS) $(MATHLIBS)
 
-test_objs = tests.o tcielabutil.o timagepixel.o
+test_objs = tests.o tcielabutil.o tcodes.o timagepixel.o
 objs = tests.o $(test_objs)
 progs = tests
 
@@ -38,10 +38,10 @@ install: all
 
 
 check: tests
-       ./tests
+       DCMDICTPATH=../../dcmdata/data/dicom.dic ./tests
 
 check-exhaustive: tests
-       ./tests -x
+       DCMDICTPATH=../../dcmdata/data/dicom.dic ./tests -x
 
 
 clean:
index 8cbab8c7abb75a5385041c01865ab0668f64e46d..c2933b3c44ffc5f02b684074da28661a6b41b5f7 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2017-2018, OFFIS e.V.
+ *  Copyright (C) 2017-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
  *
  */
 
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
-
-#include "dcmtk/ofstd/oftest.h"
-#include "dcmtk/ofstd/ofrand.h"
 #include "dcmtk/dcmiod/cielabutil.h"
-
+#include "dcmtk/ofstd/ofrand.h"
+#include "dcmtk/ofstd/oftest.h"
 
 OFTEST(dcmiod_tcielabutil)
 {
-  // Result variables for testing
-  double r1, r2, r3;
-  r1=r2=r3 = 0.0;
-
-  // Test RGB -> CIELab conversion with medium values
-  IODCIELabUtil::rgb2Lab(r1, r2, r3 /* L,a,b */, 0.5, 0.5, 0.5);
-  OFCHECK( fabs(53.388 - r1) < 0.001 );
-  OFCHECK( fabs(0.006 - r2) < 0.001 );
-  OFCHECK( fabs(-0.010 - r3) < 0.001 );
-
-  // Test RGB -> CIEXYZ conversion with medium values
-  r1=r2=r3 = 0;
-  IODCIELabUtil::rgb2Xyz(r1, r2, r3 /* X,Y,Z */, 0.5, 0.5, 0.5);
-  OFCHECK( fabs(0.203 - r1) < 0.001 );
-  OFCHECK( fabs(0.214 - r2) < 0.001 );
-  OFCHECK( fabs(0.233 - r3) < 0.001 );
-
-  // Test RGB -> CIELab conversion with minimum value
-  r1=r2=r3 = 0;
-  IODCIELabUtil::rgb2Lab(r1, r2, r3 /* L,a,b */, 0, 0, 0);
-  OFCHECK( fabs(0 - r1) < 0.001 );
-  OFCHECK( fabs(0 - r2) < 0.001 );
-  OFCHECK( fabs(0 - r3) < 0.001 );
-
-  // Test RGB -> XYZ conversion with minimum values
-  r1=r2=r3 = 0;
-  IODCIELabUtil::rgb2Xyz(r1, r2, r3 /* X,Y,Z */, 0, 0, 0);
-  OFCHECK( fabs(0 - r1) < 0.001 );
-  OFCHECK( fabs(0 - r2) < 0.001 );
-  OFCHECK( fabs(0 - r3) < 0.001 );
-
-  // Test DICOM CIELab to "normalized" CIELab conversion with maximum values
-  r1=r2=r3 = 0;
-  IODCIELabUtil::dicomlab2Lab(r1, r2, r3, 65535, 65535, 65535 );
-  OFCHECK( fabs(100 - r1) < 0.001 );
-  OFCHECK( fabs(127 - r2) < 0.001 );
-  OFCHECK( fabs(127 - r3) < 0.001 );
-
-  // Test DICOM CIELab to "normalized" CIELab conversion with minimum values
-  r1=r2=r3 = 0;
-  IODCIELabUtil::dicomlab2Lab(r1, r2, r3, 0, 0, 0 );
-  OFCHECK( fabs(0 - r1) < 0.001 );
-  OFCHECK( fabs(-128 - r2) < 0.001 );
-  OFCHECK( fabs(-128 - r3) < 0.001 );
-
-  // Convert between colorspaces back and forth and check whether deviation after
-  // roundtrip is less than around 1 promille
-
-  // Initialize random numbers
-  OFRandom rnd;
-
-  // We do 1000 runs
-  for (size_t numRun = 0; numRun< 1000; numRun++)
-  {
-    // i1, i2, i3: Input for conversion
-    // r1, r2, r3: Results of conversion
-    // o1, o2, o3: Output of inverse conversion (should equal i1, i2, i3)
-    double i1, i2, i3, o1, o2, o3;
-    i1 = i2 = i3 = r1 = r2 = r3 = o1 = o2 = o3 = 0.0;
-
-    // Roundtrip RGB -> CIELab -> RGB
-    i1 = OFstatic_cast(double,rnd.getRND32()) / OFstatic_cast(Uint32,-1);
-    i2 = OFstatic_cast(double,rnd.getRND32()) / OFstatic_cast(Uint32,-1);
-    i3 = OFstatic_cast(double,rnd.getRND32()) / OFstatic_cast(Uint32,-1);
-    IODCIELabUtil::rgb2Lab(r1, r2, r3, i1, i2, i3);
-    IODCIELabUtil::lab2Rgb(o1, o2, o3, r1, r2, r3);
-    OFCHECK( fabs(i1 - o1) < 0.001 );
-    OFCHECK( fabs(i2 - o2) < 0.001 );
-    OFCHECK( fabs(i3 - o3) < 0.001 );
-
-    // Roundtrip CIELab -> DICOM CIELab -> CIELab
-    i1 = i2 = i3 = r1 = r2 = r3 = o1 = o2 = o3 = 0.0;
-    i1 = OFstatic_cast(double,rnd.getRND32()) / OFstatic_cast(Uint32,-1) * 100.0;
-    i2 = OFstatic_cast(double,rnd.getRND32()) / OFstatic_cast(Uint32,-1) * 255.0 - 128;
-    i3 = OFstatic_cast(double,rnd.getRND32()) / OFstatic_cast(Uint32,-1) * 255.0 - 128;
-    IODCIELabUtil::lab2DicomLab(r1, r2, r3, i1, i2, i3);
-    IODCIELabUtil::dicomlab2Lab(o1, o2, o3, r1, r2, r3);
-    OFCHECK( fabs(i1 - o1) < 0.001 );
-    OFCHECK( fabs(i2 - o2) < 0.001 );
-    OFCHECK( fabs(i3 - o3) < 0.001 );
-
-    // Roundtrip RGB -> CIEXYZ -> CIELab -> dicomCIELab -> RGB
-    i1 = i2 = i3 = r1 = r2 = r3 = o1 = o2 = o3 = 0.0;
-    i1 = OFstatic_cast(double,rnd.getRND32()) / OFstatic_cast(Uint32,-1);
-    i2 = OFstatic_cast(double,rnd.getRND32()) / OFstatic_cast(Uint32,-1);
-    i3 = OFstatic_cast(double,rnd.getRND32()) / OFstatic_cast(Uint32,-1);
-    IODCIELabUtil::rgb2Xyz(r1, r2, r3, i1, i2, i3);
-    IODCIELabUtil::xyz2Lab(o1, o2, o3, r1, r2, r3);
-    IODCIELabUtil::lab2DicomLab(r1, r2, r3, o1, o2, o3);
-    IODCIELabUtil::dicomLab2RGB(o1, o2, o3, r1, r2, r3);
-
-    OFCHECK( fabs(i1 - o1) < 0.001 );
-    OFCHECK( fabs(i2 - o2) < 0.001 );
-    OFCHECK( fabs(i3 - o3) < 0.001 );
-
-  }
+    // Result variables for testing
+    double r1, r2, r3;
+    r1 = r2 = r3 = 0.0;
+
+    // Test RGB -> CIELab conversion with medium values
+    IODCIELabUtil::rgb2Lab(r1, r2, r3 /* L,a,b */, 0.5, 0.5, 0.5);
+    OFCHECK(fabs(53.388 - r1) < 0.001);
+    OFCHECK(fabs(0.006 - r2) < 0.001);
+    OFCHECK(fabs(-0.010 - r3) < 0.001);
+
+    // Test RGB -> CIEXYZ conversion with medium values
+    r1 = r2 = r3 = 0;
+    IODCIELabUtil::rgb2Xyz(r1, r2, r3 /* X,Y,Z */, 0.5, 0.5, 0.5);
+    OFCHECK(fabs(0.203 - r1) < 0.001);
+    OFCHECK(fabs(0.214 - r2) < 0.001);
+    OFCHECK(fabs(0.233 - r3) < 0.001);
+
+    // Test RGB -> CIELab conversion with minimum value
+    r1 = r2 = r3 = 0;
+    IODCIELabUtil::rgb2Lab(r1, r2, r3 /* L,a,b */, 0, 0, 0);
+    OFCHECK(fabs(0 - r1) < 0.001);
+    OFCHECK(fabs(0 - r2) < 0.001);
+    OFCHECK(fabs(0 - r3) < 0.001);
+
+    // Test RGB -> XYZ conversion with minimum values
+    r1 = r2 = r3 = 0;
+    IODCIELabUtil::rgb2Xyz(r1, r2, r3 /* X,Y,Z */, 0, 0, 0);
+    OFCHECK(fabs(0 - r1) < 0.001);
+    OFCHECK(fabs(0 - r2) < 0.001);
+    OFCHECK(fabs(0 - r3) < 0.001);
+
+    // Test DICOM CIELab to "normalized" CIELab conversion with maximum values
+    r1 = r2 = r3 = 0;
+    IODCIELabUtil::dicomlab2Lab(r1, r2, r3, 65535, 65535, 65535);
+    OFCHECK(fabs(100 - r1) < 0.001);
+    OFCHECK(fabs(127 - r2) < 0.001);
+    OFCHECK(fabs(127 - r3) < 0.001);
+
+    // Test DICOM CIELab to "normalized" CIELab conversion with minimum values
+    r1 = r2 = r3 = 0;
+    IODCIELabUtil::dicomlab2Lab(r1, r2, r3, 0, 0, 0);
+    OFCHECK(fabs(0 - r1) < 0.001);
+    OFCHECK(fabs(-128 - r2) < 0.001);
+    OFCHECK(fabs(-128 - r3) < 0.001);
+
+    // Convert between colorspaces back and forth and check whether deviation after
+    // roundtrip is less than around 1 promille
+
+    // Initialize random numbers
+    OFRandom rnd;
+
+    // We do 1000 runs
+    for (size_t numRun = 0; numRun < 1000; numRun++)
+    {
+        // i1, i2, i3: Input for conversion
+        // r1, r2, r3: Results of conversion
+        // o1, o2, o3: Output of inverse conversion (should equal i1, i2, i3)
+        double i1, i2, i3, o1, o2, o3;
+        i1 = i2 = i3 = r1 = r2 = r3 = o1 = o2 = o3 = 0.0;
+
+        // Roundtrip RGB -> CIELab -> RGB
+        i1 = OFstatic_cast(double, rnd.getRND32()) / OFstatic_cast(Uint32, -1);
+        i2 = OFstatic_cast(double, rnd.getRND32()) / OFstatic_cast(Uint32, -1);
+        i3 = OFstatic_cast(double, rnd.getRND32()) / OFstatic_cast(Uint32, -1);
+        IODCIELabUtil::rgb2Lab(r1, r2, r3, i1, i2, i3);
+        IODCIELabUtil::lab2Rgb(o1, o2, o3, r1, r2, r3);
+        OFCHECK(fabs(i1 - o1) < 0.001);
+        OFCHECK(fabs(i2 - o2) < 0.001);
+        OFCHECK(fabs(i3 - o3) < 0.001);
+
+        // Roundtrip CIELab -> DICOM CIELab -> CIELab
+        i1 = i2 = i3 = r1 = r2 = r3 = o1 = o2 = o3 = 0.0;
+        i1 = OFstatic_cast(double, rnd.getRND32()) / OFstatic_cast(Uint32, -1) * 100.0;
+        i2 = OFstatic_cast(double, rnd.getRND32()) / OFstatic_cast(Uint32, -1) * 255.0 - 128;
+        i3 = OFstatic_cast(double, rnd.getRND32()) / OFstatic_cast(Uint32, -1) * 255.0 - 128;
+        IODCIELabUtil::lab2DicomLab(r1, r2, r3, i1, i2, i3);
+        IODCIELabUtil::dicomlab2Lab(o1, o2, o3, r1, r2, r3);
+        OFCHECK(fabs(i1 - o1) < 0.001);
+        OFCHECK(fabs(i2 - o2) < 0.001);
+        OFCHECK(fabs(i3 - o3) < 0.001);
+
+        // Roundtrip RGB -> CIEXYZ -> CIELab -> dicomCIELab -> RGB
+        i1 = i2 = i3 = r1 = r2 = r3 = o1 = o2 = o3 = 0.0;
+        i1                                         = OFstatic_cast(double, rnd.getRND32()) / OFstatic_cast(Uint32, -1);
+        i2                                         = OFstatic_cast(double, rnd.getRND32()) / OFstatic_cast(Uint32, -1);
+        i3                                         = OFstatic_cast(double, rnd.getRND32()) / OFstatic_cast(Uint32, -1);
+        IODCIELabUtil::rgb2Xyz(r1, r2, r3, i1, i2, i3);
+        IODCIELabUtil::xyz2Lab(o1, o2, o3, r1, r2, r3);
+        IODCIELabUtil::lab2DicomLab(r1, r2, r3, o1, o2, o3);
+        IODCIELabUtil::dicomLab2RGB(o1, o2, o3, r1, r2, r3);
+
+        OFCHECK(fabs(i1 - o1) < 0.001);
+        OFCHECK(fabs(i2 - o2) < 0.001);
+        OFCHECK(fabs(i3 - o3) < 0.001);
+    }
 }
diff --git a/dcmiod/tests/tcodes.cc b/dcmiod/tests/tcodes.cc
new file mode 100644 (file)
index 0000000..dd959a8
--- /dev/null
@@ -0,0 +1,164 @@
+/*
+ *
+ *  Copyright (C) 2019-2020, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmect
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Tests for dcmiod's Code Sequence Macro implementation
+ *
+ */
+
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+#include "dcmtk/dcmiod/iodmacro.h"
+#include "dcmtk/ofstd/oftest.h"
+
+static OFLogger tCodeLogger = OFLog::getLogger("dcmtk.test.t_codes");
+
+static void clearCode(CodeSequenceMacro& c);
+
+OFTEST(dcmiod_codes)
+{
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
+    // Most basic, classic "Code Value" variant
+    CodeSequenceMacro c("Value", "99DCMTK", "Classic code", "Version 1");
+    OFCHECK(c.check().good());
+    OFString val;
+    OFCHECK(c.getCodeValue(val, -1, OFTrue /* autoTag */).good());
+    OFCHECK(val == "Value");
+    OFCHECK(c.getCodeValue(val, -1, OFFalse /* autoTag off */).good());
+    OFCHECK(val == "Value");
+    OFCHECK(c.getCodingSchemeDesignator(val).good());
+    OFCHECK(val == "99DCMTK");
+    OFCHECK(c.getCodeMeaning(val).good());
+    OFCHECK(val == "Classic code");
+    OFCHECK(c.getCodingSchemeVersion(val).good());
+    OFCHECK(val == "Version 1");
+    OFCHECK(c.getLongCodeValue(val).bad());
+    OFCHECK(c.getURNCodeValue(val).bad());
+    OFCHECK(c.check().good());
+
+    clearCode(c);
+    val.clear();
+
+    // "URN Code Value" variant
+    OFCHECK(c.set("http://www.open-connections.de", "99DCMTK", "URN code", "Version 1", OFTrue, OFTrue /* autoTag */)
+                .good());
+    OFCHECK(c.check().good());
+    OFCHECK(c.getCodeValue(val, -1, OFTrue /* autoTag */).good());
+    OFCHECK(val == "http://www.open-connections.de");
+    val.clear();
+    OFCHECK(c.getCodeValue(val, -1, OFFalse /* autoTag off */).bad());
+    OFCHECK(val.empty());
+    OFCHECK(c.getCodingSchemeDesignator(val).good());
+    OFCHECK(val == "99DCMTK");
+    OFCHECK(c.getCodeMeaning(val).good());
+    OFCHECK(val == "URN code");
+    OFCHECK(c.getCodingSchemeVersion(val).good());
+    OFCHECK(val == "Version 1");
+    OFCHECK(c.getLongCodeValue(val).bad());
+    OFCHECK(c.getURNCodeValue(val).good());
+    OFCHECK(val == "http://www.open-connections.de");
+    OFCHECK(c.check().good());
+
+    clearCode(c);
+    val.clear();
+
+    // "Long Code Value" variant
+    OFCHECK(c.set("Open Connections GmbH", "99DCMTK", "Long code", "Version 1", OFTrue, OFTrue /* autoTag */).good());
+    OFCHECK(c.check().good());
+    OFCHECK(c.getCodeValue(val, -1, OFTrue /* autoTag */).good());
+    OFCHECK(val == "Open Connections GmbH");
+    val.clear();
+    OFCHECK(c.getCodeValue(val, -1, OFFalse /* autoTag off */).bad());
+    OFCHECK(val.empty());
+    OFCHECK(c.getCodingSchemeDesignator(val).good());
+    OFCHECK(val == "99DCMTK");
+    OFCHECK(c.getCodeMeaning(val).good());
+    OFCHECK(val == "Long code");
+    OFCHECK(c.getCodingSchemeVersion(val).good());
+    OFCHECK(val == "Version 1");
+    OFCHECK(c.getURNCodeValue(val).bad());
+    OFCHECK(c.getLongCodeValue(val).good());
+    OFCHECK(val == "Open Connections GmbH");
+    OFCHECK(c.check().good());
+
+    clearCode(c);
+    val.clear();
+
+    // Check only single code value is set internally (old values are deleted)
+    OFCHECK(c.set("http://www.open-connections.de", "99DCMTK", "URN code", "Version 1", OFTrue, OFTrue /* autoTag */)
+                .good());
+    OFCHECK(c.set("Value", "99DCMTK", "Classic code", "Version 1").good());
+    OFCHECK(c.getLongCodeValue(val).bad());
+    OFCHECK(c.getURNCodeValue(val).bad());
+
+    clearCode(c);
+    val.clear();
+
+    OFCHECK(c.set("http://www.open-connections.de", "99DCMTK", "URN code", "Version 1", OFTrue, OFTrue /* autoTag */)
+                .good());
+    OFCHECK(c.set("Open Connections GmbH", "99DCMTK", "Long code", "Version 1", OFTrue, OFTrue /* autoTag */).good());
+    OFCHECK(c.getURNCodeValue(val).bad());
+    OFCHECK(c.getCodeValue(val, -1, OFFalse /*autoTag off */).bad());
+
+    clearCode(c);
+    val.clear();
+
+    // Failure: URN Code Value without autoTag
+    OFCHECK(c.set("http://www.open-connections.de/this/url/is/over/64/characters/long",
+                  "99DCMTK",
+                  "URN code",
+                  "Version 1",
+                  OFTrue,
+                  OFFalse /* autoTag off */)
+                .bad());
+    OFCHECK(c.check().bad());
+
+    clearCode(c);
+    val.clear();
+
+    // Failure: Long Code Value without autoTag
+    OFCHECK(c.set("Open Connections GmbH, Oldenburg, Germany, c/o Name over 64 characters long",
+                  "99DCMTK",
+                  "URN code",
+                  "Version 1",
+                  OFTrue,
+                  OFFalse /* autoTag off */)
+                .bad());
+    OFCHECK(c.check().bad());
+}
+
+static void clearCode(CodeSequenceMacro& c)
+{
+    c.clearData();
+    OFString val;
+    c.getCodeValue(val);
+    OFCHECK(val.empty());
+    c.getURNCodeValue(val);
+    OFCHECK(val.empty());
+    c.getLongCodeValue(val);
+    OFCHECK(val.empty());
+    c.getCodingSchemeDesignator(val);
+    OFCHECK(val.empty());
+    c.getCodeMeaning(val);
+    OFCHECK(val.empty());
+    c.getCodingSchemeVersion(val);
+    OFCHECK(val.empty());
+}
index c1528a9c24dfeb1b71ee1c1e81a4e3d16ac47e64..f450a82a649415e41f542f23f42556fbc0a48597 100644 (file)
@@ -22,6 +22,7 @@
 #include "dcmtk/config/osconfig.h"
 #include "dcmtk/ofstd/oftest.h"
 
+OFTEST_REGISTER(dcmiod_codes);
 OFTEST_REGISTER(dcmiod_tcielabutil);
 OFTEST_REGISTER(dcmiod_imagepixel);
 OFTEST_MAIN("dcmiod")
index 2c4ed75fe51ad4f74c036363d46aa2a59be2aed3..9b997ccf2311811159b956ca325ce62131edbd43 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016, OFFIS e.V.
+ *  Copyright (C) 2016-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
  *
  *  Author:  Jan Schlamelcher
  *
- *  Purpose: Tests for dcmiod's color conversion functionalities
+ *  Purpose: Tests for Image Pixel Module functionalities
  *
  */
 
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
-
-#include "dcmtk/ofstd/oftest.h"
 #include "dcmtk/dcmiod/iodimage.h"
-#include "dcmtk/dcmiod/modimagepixel.h"
 #include "dcmtk/dcmiod/modfloatingpointimagepixel.h"
+#include "dcmtk/dcmiod/modimagepixel.h"
+#include "dcmtk/ofstd/oftest.h"
 
 OFTEST(dcmiod_imagepixel)
 {
-  DcmIODImage<IODImagePixelModule<Uint8>,IODFloatingPointImagePixelModule> image1;
-  DcmIODImage<IODImagePixelModule<Uint8>,IODImagePixelModule<Uint8>,IODDoubleFloatingPointImagePixelModule> image2( OFin_place<IODImagePixelModule<Uint8> > );
+    DcmIODImage<IODImagePixelModule<Uint8>, IODFloatingPointImagePixelModule> image1;
+    DcmIODImage<IODImagePixelModule<Uint8>, IODImagePixelModule<Uint8>, IODDoubleFloatingPointImagePixelModule> image2(
+        OFin_place<IODImagePixelModule<Uint8> >);
 }
index b43ee65ae3e94bb72bd7310ce427f475ef2cc06b..1ed23296ee3948e4ab4f77fab72cfdd98e24ae7d 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2001-2019, OFFIS e.V.
+ *  Copyright (C) 2001-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -57,7 +57,7 @@ int main(int argc, char *argv[])
   const char *opt_ofname = NULL;
 
   E_FileReadMode opt_readMode = ERM_autoDetect;
-  E_FileWriteMode opt_writeMode = EWM_fileformat;
+  E_FileWriteMode opt_writeMode = EWM_createNewMeta;
   E_TransferSyntax opt_oxfer = EXS_LittleEndianExplicit;
   E_GrpLenEncoding opt_oglenc = EGL_recalcGL;
   E_EncodingType opt_oenctype = EET_ExplicitLength;
@@ -217,7 +217,7 @@ int main(int argc, char *argv[])
       cmd.endOptionBlock();
 
       cmd.beginOptionBlock();
-      if (cmd.findOption("--write-file")) opt_writeMode = EWM_fileformat;
+      if (cmd.findOption("--write-file")) opt_writeMode = EWM_createNewMeta;
       if (cmd.findOption("--write-dataset")) opt_writeMode = EWM_dataset;
       cmd.endOptionBlock();
 
@@ -326,10 +326,6 @@ int main(int argc, char *argv[])
 
     OFLOG_INFO(dcmdjpegLogger, "creating output file " << opt_ofname);
 
-    // update file meta information with new SOP Instance UID
-    if ((opt_uidcreation == EUC_always) && (opt_writeMode == EWM_fileformat))
-        opt_writeMode = EWM_updateMeta;
-
     fileformat.loadAllDataIntoMemory();
     error = fileformat.saveFile(opt_ofname, opt_oxfer, opt_oenctype, opt_oglenc,
         opt_opadenc, OFstatic_cast(Uint32, opt_filepad), OFstatic_cast(Uint32, opt_itempad), opt_writeMode);
index 7804b8bc74f0543d800d6c735468f0f1d74e57ac..2b982b8d5751b4d0e0c1655ee5e2d84fca551169 100644 (file)
@@ -127,7 +127,7 @@ flipping:
 scaling:
 
   +a    --recognize-aspect
-          recognize pixel aspect ratio (default)
+          recognize pixel aspect ratio when scaling (default)
 
   -a    --ignore-aspect
           ignore pixel aspect ratio when scaling
@@ -397,7 +397,7 @@ JPEG format:
 other transformations:
 
   +G    --grayscale
-          convert to grayscale if necessary
+          convert color image to grayscale (monochrome)
 
   +P    --change-polarity
           change polarity (invert pixel output)
@@ -574,6 +574,6 @@ It is an error if no data dictionary can be loaded.
 
 \section dcmj2pnm_copyright COPYRIGHT
 
-Copyright (C) 2001-2018 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 2001-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index 147d3d098b82c89dd13f5946fb77ef0540a6994c..4f59d07cd7ec74f0a1f78c612734a90fb87f53d7 100644 (file)
@@ -39,11 +39,6 @@ if (fileformat.loadFile("test.dcm").good())
   if (dataset->chooseRepresentation(EXS_JPEGProcess14SV1, &params).good() &&
       dataset->canWriteXfer(EXS_JPEGProcess14SV1))
   {
-    // force the meta-header UIDs to be re-generated when storing the file
-    // since the UIDs in the data set may have changed
-    delete metaInfo->remove(DCM_MediaStorageSOPClassUID);
-    delete metaInfo->remove(DCM_MediaStorageSOPInstanceUID);
-
     // store in lossless JPEG format
     fileformat.saveFile("test_jpeg.dcm", EXS_JPEGProcess14SV1);
   }
index 4a747ce9001038a125317cf29bc66fd22393eec3..7c31575d838712859b309ea62ef88c0218b9bd43 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2001-2017, OFFIS e.V.
+ *  Copyright (C) 2001-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -61,6 +61,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition decode(
@@ -68,7 +72,8 @@ public:
     DcmPixelSequence * pixSeq,
     DcmPolymorphOBOW& uncompressedPixelData,
     const DcmCodecParameter * cp,
-    const DcmStack& objStack) const;
+    const DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** decompresses a single frame from the given pixel sequence and
    *  stores the result in the given buffer.
@@ -118,6 +123,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition encode(
@@ -126,7 +135,8 @@ public:
     const DcmRepresentationParameter * toRepParam,
     DcmPixelSequence * & pixSeq,
     const DcmCodecParameter *cp,
-    DcmStack & objStack) const;
+    DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** transcodes (re-compresses) the given compressed DICOM image and stores
    *  the result in the given toPixSeq element.
@@ -140,6 +150,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition encode(
@@ -149,7 +163,8 @@ public:
     const DcmRepresentationParameter * toRepParam,
     DcmPixelSequence * & toPixSeq,
     const DcmCodecParameter * cp,
-    DcmStack & objStack) const;
+    DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** checks if this codec is able to convert from the
    *  given current transfer syntax to the given new
index 9fda0226a410e22b23a82207cffb4bf721f45744..b521bab1bea6b3738a4107596290da4bd83d5059 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2001-2014, OFFIS e.V.
+ *  Copyright (C) 2001-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -65,6 +65,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition decode(
@@ -72,7 +76,8 @@ public:
     DcmPixelSequence * pixSeq,
     DcmPolymorphOBOW& uncompressedPixelData,
     const DcmCodecParameter * cp,
-    const DcmStack& objStack) const;
+    const DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** decompresses a single frame from the given pixel sequence and
    *  stores the result in the given buffer.
@@ -122,6 +127,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition encode(
@@ -130,7 +139,8 @@ public:
     const DcmRepresentationParameter * toRepParam,
     DcmPixelSequence * & pixSeq,
     const DcmCodecParameter *cp,
-    DcmStack & objStack) const;
+    DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** transcodes (re-compresses) the given compressed DICOM image and stores
    *  the result in the given toPixSeq element.
@@ -144,6 +154,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition encode(
@@ -153,7 +167,8 @@ public:
     const DcmRepresentationParameter * toRepParam,
     DcmPixelSequence * & toPixSeq,
     const DcmCodecParameter * cp,
-    DcmStack & objStack) const;
+    DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** checks if this codec is able to convert from the
    *  given current transfer syntax to the given new
index f7280d97d7da272f3c4e5c4ede71b34279de6391..c13d4673caa07b0853e08cd0d0cae335d5c22695 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2001-2018, OFFIS e.V.
+ *  Copyright (C) 2001-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -65,9 +65,16 @@ OFCondition DJCodecDecoder::decode(
     DcmPixelSequence * pixSeq,
     DcmPolymorphOBOW& uncompressedPixelData,
     const DcmCodecParameter * cp,
-    const DcmStack& objStack) const
+    const DcmStack& objStack,
+    OFBool& removeOldRep) const
 {
   OFCondition result = EC_Normal;
+
+  // this codec may modify the DICOM header such that the previous pixel
+  // representation is not valid anymore. Indicate this to the caller
+  // to trigger removal.
+  removeOldRep = OFTrue;
+
   // assume we can cast the codec parameter to what we need
   const DJCodecParameter *djcp = OFreinterpret_cast(const DJCodecParameter*, cp);
 
@@ -594,7 +601,8 @@ OFCondition DJCodecDecoder::encode(
     const DcmRepresentationParameter * /* toRepParam */,
     DcmPixelSequence * & /* pixSeq */,
     const DcmCodecParameter * /* cp */,
-    DcmStack & /* objStack */) const
+    DcmStack & /* objStack */,
+    OFBool& /* removeOldRep */) const
 {
   // we are a decoder only
   return EC_IllegalCall;
@@ -608,7 +616,8 @@ OFCondition DJCodecDecoder::encode(
     const DcmRepresentationParameter * /* toRepParam */,
     DcmPixelSequence * & /* toPixSeq */,
     const DcmCodecParameter * /* cp */,
-    DcmStack & /* objStack */) const
+    DcmStack & /* objStack */,
+    OFBool& /* removeOldRep */) const
 {
   // we don't support re-coding for now
   return EC_IllegalCall;
index f61d953148c4054e93336b77535bfb67aab96c4a..b052e0d52f5edce785a82e1a7e3b8330e948445f 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2001-2019, OFFIS e.V.
+ *  Copyright (C) 2001-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -81,7 +81,8 @@ OFCondition DJCodecEncoder::decode(
   DcmPixelSequence * /* pixSeq */,
   DcmPolymorphOBOW& /* uncompressedPixelData */,
   const DcmCodecParameter * /* cp */,
-  const DcmStack& /* objStack */) const
+  const DcmStack& /* objStack */,
+  OFBool& /* removeOldRep */ ) const
 {
   // we are an encoder only
   return EC_IllegalCall;
@@ -111,7 +112,8 @@ OFCondition DJCodecEncoder::encode(
   const DcmRepresentationParameter * /* toRepParam */,
   DcmPixelSequence * & /* toPixSeq */,
   const DcmCodecParameter * /* cp */,
-  DcmStack & /* objStack */) const
+  DcmStack & /* objStack */,
+  OFBool& /* removeOldRep */) const
 {
   // we don't support re-coding for now
   return EC_IllegalCall;
@@ -124,9 +126,16 @@ OFCondition DJCodecEncoder::encode(
   const DcmRepresentationParameter * toRepParam,
   DcmPixelSequence * & pixSeq,
   const DcmCodecParameter *cp,
-  DcmStack & objStack) const
+  DcmStack & objStack,
+  OFBool& removeOldRep) const
 {
   OFCondition result = EC_Normal;
+
+  // this codec may modify the DICOM header such that the previous pixel
+  // representation is not valid anymore. Indicate this to the caller
+  // to trigger removal.
+  removeOldRep = OFTrue;
+
   // assume we can cast the codec parameter to what we need
   const DJCodecParameter *djcp = OFreinterpret_cast(const DJCodecParameter*, cp);
 
@@ -823,10 +832,9 @@ OFCondition DJCodecEncoder::updateDerivationDescription(
     // assume we can cast the codec parameter to what we need
     DJCodecParameter *djcp = OFconst_cast(DJCodecParameter*, cp);
 
-    if (djcp->getTrueLosslessMode())
-      result = DcmCodec::insertCodeSequence(dataset, DCM_DerivationCodeSequence, "DCM", "121327", "Full fidelity image");
-    else // pseudo-lossless mode may also result in lossy compression
+    if (!isLosslessProcess() || !djcp->getTrueLosslessMode())
       result = DcmCodec::insertCodeSequence(dataset, DCM_DerivationCodeSequence, "DCM", "113040", "Lossy Compression");
+
   }
   return result;
 }
index 2a9a4526ee00dc19102a09a334cbd549720325e7..0cb3f53ed1eb1925017fe79875fc50fc05f23ce1 100644 (file)
@@ -8,5 +8,5 @@ endforeach()
 
 # make sure executables are linked to the corresponding libraries
 foreach(PROGRAM dcmcjpls dcmdjpls dcml2pnm)
-  DCMTK_TARGET_LINK_MODULES(${PROGRAM} dcmjpls charls dcmimage dcmimgle dcmdata oflog ofstd ofstd)
+  DCMTK_TARGET_LINK_MODULES(${PROGRAM} dcmjpls dcmtkcharls dcmimage dcmimgle dcmdata oflog ofstd ofstd)
 endforeach()
index 33ef2597f66d06d0fd14512c5861908f36ac3c44..58608a192f917a134d52b3a05aa783b944c44adb 100644 (file)
@@ -44,7 +44,7 @@ dcmjplslib = -ldcmjpls
 
 libcharlsdir = $(dcmjplsdir)
 libcharlslibdir = -L$(dcmjplsdir)/libcharls
-libcharlslib = -lcharls
+libcharlslib = -ldcmtkcharls
 
 LOCALINCLUDES = $(dcmjplsinc) $(ofstdinc) $(ofloginc) $(dcmdatainc) $(dcmimageinc) $(dcmimgleinc)
 LIBDIRS = -L$(top_srcdir)/libsrc $(dcmjplslibdir) $(libcharlslibdir) $(dcmimagelibdir) \
index 9e958d5330ce098a814181e8447156a9de915e3e..b1f3eafea661fc8a2e4e76366f6dc0cb65ae47de 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2007-2019, OFFIS e.V.
+ *  Copyright (C) 2007-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -152,7 +152,9 @@ LICENSE_FILE_DECLARE_COMMAND_LINE_OPTIONS
     cmd.addSubGroup("JPEG-LS interleave:");
       cmd.addOption("--interleave-line",        "+il",    "force line-interleaved JPEG-LS images (default)");
       cmd.addOption("--interleave-sample",      "+is",    "force sample-interleaved JPEG-LS images");
+#ifdef ENABLE_DCMJPLS_INTERLEAVE_NONE
       cmd.addOption("--interleave-none",        "+in",    "force uninterleaved JPEG-LS images");
+#endif
       cmd.addOption("--interleave-default",     "+iv",    "use the fastest possible interleave mode");
     cmd.addSubGroup("JPEG-LS padding of odd-length bitstreams:");
       cmd.addOption("--padding-standard",       "+ps",    "pad with extended EOI marker (default)");
@@ -321,10 +323,12 @@ LICENSE_FILE_EVALUATE_COMMAND_LINE_OPTIONS
       {
         opt_interleaveMode = DJLSCodecParameter::interleaveLine;
       }
+#ifdef ENABLE_DCMJPLS_INTERLEAVE_NONE
       if (cmd.findOption("--interleave-none"))
       {
         opt_interleaveMode = DJLSCodecParameter::interleaveNone;
       }
+#endif
       cmd.endOptionBlock();
 
       // padding
index 006ddad3bfa725adb51ac1d2d56b6e5cb6b5de0c..df0ac974fdf445fc49cb6cd09f41606a760b69fa 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2007-2019, OFFIS e.V.
+ *  Copyright (C) 2007-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -69,7 +69,7 @@ int main(int argc, char *argv[])
   OFCmdUnsignedInt opt_filepad = 0;
   OFCmdUnsignedInt opt_itempad = 0;
   E_FileReadMode opt_readMode = ERM_autoDetect;
-  E_FileWriteMode opt_writeMode = EWM_fileformat;
+  E_FileWriteMode opt_writeMode = EWM_createNewMeta;
   E_TransferSyntax opt_ixfer = EXS_Unknown;
   OFBool opt_forceSingleFragmentPerFrame = OFFalse;
 
@@ -212,7 +212,7 @@ LICENSE_FILE_EVALUATE_COMMAND_LINE_OPTIONS
       cmd.endOptionBlock();
 
       cmd.beginOptionBlock();
-      if (cmd.findOption("--write-file")) opt_writeMode = EWM_fileformat;
+      if (cmd.findOption("--write-file")) opt_writeMode = EWM_createNewMeta;
       if (cmd.findOption("--write-dataset")) opt_writeMode = EWM_dataset;
       cmd.endOptionBlock();
 
@@ -315,10 +315,6 @@ LICENSE_FILE_EVALUATE_COMMAND_LINE_OPTIONS
 
     OFLOG_INFO(dcmdjplsLogger, "creating output file " << opt_ofname);
 
-    // update file meta information with new SOP Instance UID
-    if (opt_uidcreation && (opt_writeMode == EWM_fileformat))
-        opt_writeMode = EWM_updateMeta;
-
     fileformat.loadAllDataIntoMemory();
     error = fileformat.saveFile(opt_ofname, opt_oxfer, opt_oenctype, opt_oglenc, opt_opadenc,
       OFstatic_cast(Uint32, opt_filepad), OFstatic_cast(Uint32, opt_itempad), opt_writeMode);
index b5180db789587a3d94d39107eca9f602cfea1d26..bf16e4c34785e26649c7d7e39957f343fd37912b 100644 (file)
@@ -162,13 +162,6 @@ JPEG-LS interleave:
   # In sample-interleave mode each pixel's components are encoded before
   # the next pixel is encoded.
 
-  +in  --interleave-none
-         force uninterleaved JPEG-LS images
-
-  # This flag forces uninterleaved mode for the resulting image.
-  # In this mode, each of the image's components are completely encoded
-  # before the next component is handled.
-
   +iv  --interleave-default
          use the fastest possible interleave mode
 
@@ -395,6 +388,6 @@ It is an error if no data dictionary can be loaded.
 
 \section dcmcjpls_copyright COPYRIGHT
 
-Copyright (C) 2009-2019 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 2009-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index 9db860a51da7cbe10c34b4ffa2f95c0543c64a2c..1cee5fa791b12f65291a8906ed41e915178d2fc1 100644 (file)
@@ -41,11 +41,6 @@ if (fileformat.loadFile("test.dcm").good())
   // check if everything went well
   if (dataset->canWriteXfer(EXS_JPEGLSLossless))
   {
-    // force the meta-header UIDs to be re-generated when storing the file
-    // since the UIDs in the data set may have changed
-    delete metaInfo->remove(DCM_MediaStorageSOPClassUID);
-    delete metaInfo->remove(DCM_MediaStorageSOPInstanceUID);
-
     // store in lossless JPEG-LS format
     fileformat.saveFile("test_jpls.dcm", EXS_JPEGLSLossless);
   }
@@ -76,12 +71,12 @@ DJLSDecoderRegistration::cleanup(); // deregister JPEG-LS codecs
 
 \section Legal Legal Remark
 
-Please note that Hewlett Packard claims to own patents that apply to 
-JPEG-LS. Hewlett Packard grants free licenses for conformant 
-implementations of JPEG-LS. OFFIS as the author of the DCMTK toolkit 
-has obtained such a license, but depending on your national 
-legislations companies that use DCMTK's JPEG-LS codec may need to 
-also acquire a license. Read more at http://www.hpl.hp.com/loco/ if 
+Please note that Hewlett Packard claims to own patents that apply to
+JPEG-LS. Hewlett Packard grants free licenses for conformant
+implementations of JPEG-LS. OFFIS as the author of the DCMTK toolkit
+has obtained such a license, but depending on your national
+legislations companies that use DCMTK's JPEG-LS codec may need to
+also acquire a license. Read more at http://www.hpl.hp.com/loco/ if
 you intend to use this module for commercial purposes.
 
 */
index a5044f4e8cc70f5b8a67ec46e5f8a27e9b5fdcf8..e9b379673308e98d3729fd12871a71fa1db36e60 100644 (file)
@@ -127,7 +127,7 @@ flipping:
 scaling:
 
   +a    --recognize-aspect
-          recognize pixel aspect ratio (default)
+          recognize pixel aspect ratio when scaling (default)
 
   -a    --ignore-aspect
           ignore pixel aspect ratio when scaling
@@ -328,7 +328,7 @@ PNG format:
 other transformations:
 
   +G    --grayscale
-          convert to grayscale if necessary
+          convert color image to grayscale (monochrome)
 
   +P    --change-polarity
           change polarity (invert pixel output)
@@ -498,6 +498,6 @@ It is an error if no data dictionary can be loaded.
 
 \section dcml2pnm_copyright COPYRIGHT
 
-Copyright (C) 2001-2014 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 2001-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index 71c5de79f691b0898bac1b8fab2685b2f728b79d..611d9b4d68fc1675a6e781c18409cf3266d23f21 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2007-2017, OFFIS e.V.
+ *  Copyright (C) 2007-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -54,6 +54,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition decode(
@@ -61,7 +65,8 @@ public:
     DcmPixelSequence * pixSeq,
     DcmPolymorphOBOW& uncompressedPixelData,
     const DcmCodecParameter * cp,
-    const DcmStack& objStack) const;
+    const DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** decompresses a single frame from the given pixel sequence and
    *  stores the result in the given buffer.
@@ -111,6 +116,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition encode(
@@ -119,7 +128,8 @@ public:
     const DcmRepresentationParameter * toRepParam,
     DcmPixelSequence * & pixSeq,
     const DcmCodecParameter *cp,
-    DcmStack & objStack) const;
+    DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** transcodes (re-compresses) the given compressed DICOM image and stores
    *  the result in the given toPixSeq element.
@@ -133,6 +143,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition encode(
@@ -142,7 +156,8 @@ public:
     const DcmRepresentationParameter * toRepParam,
     DcmPixelSequence * & toPixSeq,
     const DcmCodecParameter * cp,
-    DcmStack & objStack) const;
+    DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** checks if this codec is able to convert from the
    *  given current transfer syntax to the given new
index e2dbc4f8d20771b0aca4b81771510c0286174a7e..01209c2551792ce234ae849c2070bf031dc964cd 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2007-2019, OFFIS e.V.
+ *  Copyright (C) 2007-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -57,6 +57,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition decode(
@@ -64,7 +68,8 @@ public:
     DcmPixelSequence * pixSeq,
     DcmPolymorphOBOW& uncompressedPixelData,
     const DcmCodecParameter * cp,
-    const DcmStack& objStack) const;
+    const DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** decompresses a single frame from the given pixel sequence and
    *  stores the result in the given buffer.
@@ -114,6 +119,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition encode(
@@ -122,7 +131,8 @@ public:
     const DcmRepresentationParameter * toRepParam,
     DcmPixelSequence * & pixSeq,
     const DcmCodecParameter *cp,
-    DcmStack & objStack) const;
+    DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** transcodes (re-compresses) the given compressed DICOM image and stores
    *  the result in the given toPixSeq element.
@@ -136,6 +146,10 @@ public:
    *  @param cp codec parameters for this codec
    *  @param objStack stack pointing to the location of the pixel data
    *    element in the current dataset.
+   *  @param removeOldRep boolean flag that should be set to false before this method call
+   *    and will be set to true if the codec modifies the DICOM dataset such
+   *    that the pixel data of the original representation may not be usable
+   *    anymore.
    *  @return EC_Normal if successful, an error code otherwise.
    */
   virtual OFCondition encode(
@@ -145,7 +159,8 @@ public:
     const DcmRepresentationParameter * toRepParam,
     DcmPixelSequence * & toPixSeq,
     const DcmCodecParameter * cp,
-    DcmStack & objStack) const;
+    DcmStack & objStack,
+    OFBool& removeOldRep) const;
 
   /** checks if this codec is able to convert from the
    *  given current transfer syntax to the given new
index 524fd73624cdbb1de9b1dc37379f53224c7bbb14..cce6ca42ad4ae316c6a75dd9ff2672aca4239721 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1997-2019, OFFIS e.V.
+ *  Copyright (C) 1997-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -42,9 +42,12 @@ public:
     /// Sample-interleaved (color-by-pixel)
     interleaveSample,
     /// Line-interleaved (color-by-line)
-    interleaveLine,
+    interleaveLine
+#ifdef ENABLE_DCMJPLS_INTERLEAVE_NONE
+    ,
     /// Uninterleaved (color-by-plane)
     interleaveNone
+#endif
   };
 
   /** constructor, for use with encoders.
index 0c5b14335c218382583d63753ef9deaa3ff7db7e..ae0c01728790429bd836dbc39993271bf3e164c8 100644 (file)
@@ -2,6 +2,6 @@
 include_directories("${dcmjpls_SOURCE_DIR}/libcharls" "${ofstd_SOURCE_DIR}/include")
 
 # create library from source files
-DCMTK_ADD_LIBRARY(charls header intrface jpegls)
+DCMTK_ADD_LIBRARY(dcmtkcharls header intrface jpegls)
 
-DCMTK_TARGET_LINK_MODULES(charls ofstd oflog)
+DCMTK_TARGET_LINK_MODULES(dcmtkcharls ofstd oflog)
index d26877c4b0ace331aca80dfa5f1dda58f2a91e95..a6f1f4675ca05fa786ee207295e03f878acf4809 100644 (file)
@@ -19,7 +19,7 @@ LOCALDEFS =
 
 objs = header.o intrface.o jpegls.o
 
-library = libcharls.$(LIBEXT)
+library = libdcmtkcharls.$(LIBEXT)
 
 all: $(library)
 
index 8e9a0504046a638f61e74bd420a153ece8788739..8c8cd52111a7613f51acd82c2180106a428ea6e8 100644 (file)
@@ -1,6 +1,6 @@
-// 
-// (C) Jan de Vaan 2007-2010, all rights reserved. See the accompanying "License.txt" for licensed use. 
-// 
+//
+// (C) Jan de Vaan 2007-2010, all rights reserved. See the accompanying "License.txt" for licensed use.
+//
 
 #include "config.h"
 #include "util.h"
@@ -68,12 +68,12 @@ JLS_ERROR CheckParameterCoherent(const JlsParameters* pparams)
 
        switch (pparams->components)
        {
-               case 4: return pparams->ilv == ILV_SAMPLE ? ParameterValueNotSupported : OK; 
+               case 4: return pparams->ilv == ILV_SAMPLE ? ParameterValueNotSupported : OK;
                case 3: return OK;
                case 1: return pparams->ilv != ILV_NONE ? ParameterValueNotSupported : OK;
                case 0: return InvalidJlsParameters;
 
-               default: return pparams->ilv != ILV_NONE ? ParameterValueNotSupported : OK; 
+               default: return pparams->ilv != ILV_NONE ? ParameterValueNotSupported : OK;
        }
 }
 
@@ -94,7 +94,7 @@ public:
                pstream->WriteByte(0xFF);
                pstream->WriteByte(_marker);
                pstream->WriteWord(USHORT(_vecbyte.size() + 2));
-               pstream->WriteBytes(_vecbyte);          
+               pstream->WriteBytes(_vecbyte);
        }
 
        BYTE _marker;
@@ -109,7 +109,7 @@ void push_back(OFVector<BYTE>& vec, USHORT value)
 {
        vec.push_back(BYTE(value / 0x100));
        vec.push_back(BYTE(value % 0x100));
-}                                 
+}
 
 
 //
@@ -122,16 +122,16 @@ JpegSegment* CreateMarkerStartOfFrame(Size size, LONG bitsPerSample, LONG ccomp)
        vec.push_back(static_cast<BYTE>(bitsPerSample));
        push_back(vec, static_cast<USHORT>(size.cy));
        push_back(vec, static_cast<USHORT>(size.cx));
-       
+
        // components
        vec.push_back(static_cast<BYTE>(ccomp));
        for (BYTE component = 0; component < ccomp; component++)
        {
                // rescaling
                vec.push_back(component + 1);
-               vec.push_back(0x11); 
+               vec.push_back(0x11);
                //"Tq1" reserved, 0
-               vec.push_back(0);               
+               vec.push_back(0);
        }
 
        return new JpegMarkerSegment(JPEG_SOF, vec);
@@ -161,7 +161,6 @@ JLSOutputStream::~JLSOutputStream()
        {
                delete _segments[i];
        }
-       _segments.empty();
 }
 
 
@@ -172,7 +171,7 @@ JLSOutputStream::~JLSOutputStream()
 //
 void JLSOutputStream::Init(Size size, LONG bitsPerSample, LONG ccomp)
 {
-               _segments.push_back(CreateMarkerStartOfFrame(size, bitsPerSample, ccomp));
+       _segments.push_back(CreateMarkerStartOfFrame(size, bitsPerSample, ccomp));
 }
 
 
@@ -184,8 +183,8 @@ void JLSOutputStream::AddColorTransform(int i)
        rgbyteXform.push_back('f');
        rgbyteXform.push_back('x');
        rgbyteXform.push_back((BYTE)i);
-                       
-       _segments.push_back(new JpegMarkerSegment(JPEG_APP8, rgbyteXform));     
+
+       _segments.push_back(new JpegMarkerSegment(JPEG_APP8, rgbyteXform));
 }
 
 
@@ -201,7 +200,7 @@ size_t JLSOutputStream::Write(BYTE **ptr, size_t *size, size_t offset)
        WriteByte(0xFF);
 
        WriteByte(JPEG_SOI);
-       
+
        for (size_t i = 0; i < _segments.size(); ++i)
        {
                _segments[i]->Write(this);
@@ -263,7 +262,7 @@ void JLSInputStream::ReadPixels(void* pvoid, size_t cbyteAvailable)
 
        if (cbyteAvailable < cbytePlane * _info.components)
                throw JlsException(UncompressedBufferTooSmall);
-       
+
        int scancount = _info.ilv == ILV_NONE ? _info.components : 1;
 
        BYTE* pbyte = (BYTE*)pvoid;
@@ -271,7 +270,7 @@ void JLSInputStream::ReadPixels(void* pvoid, size_t cbyteAvailable)
        {
                ReadScan(pbyte);
                pbyte += cbytePlane;
-       }       
+       }
 }
 
 // ReadNBytes()
@@ -295,7 +294,7 @@ void JLSInputStream::ReadHeader()
 
        if (ReadByte() != JPEG_SOI)
                throw JlsException(InvalidCompressedData);
-       
+
        for (;;)
        {
                if (ReadByte() != 0xFF)
@@ -314,13 +313,13 @@ void JLSInputStream::ReadHeader()
                        case JPEG_LSE: ReadPresetParameters();  break;
                        case JPEG_APP0: ReadJfif(); break;
                        case JPEG_APP7: ReadColorSpace(); break;
-                       case JPEG_APP8: ReadColorXForm(); break;                        
+                       case JPEG_APP8: ReadColorXForm(); break;
                        // Other tags not supported (among which DNL DRI)
                        default:                throw JlsException(ImageTypeNotSupported);
                }
 
                if (marker == JPEG_SOS)
-               {                               
+               {
                        _cbyteOffset = cbyteStart - 2;
                        return;
                }
@@ -332,7 +331,7 @@ void JLSInputStream::ReadHeader()
 JpegMarkerSegment* EncodeStartOfScan(const JlsParameters* pparams, LONG icomponent)
 {
        BYTE itable             = 0;
-       
+
        OFVector<BYTE> rgbyte;
 
        if (icomponent < 0)
@@ -348,7 +347,7 @@ JpegMarkerSegment* EncodeStartOfScan(const JlsParameters* pparams, LONG icompone
        {
                rgbyte.push_back(1);
                rgbyte.push_back((BYTE)icomponent);
-               rgbyte.push_back(itable);       
+               rgbyte.push_back(itable);
        }
 
        rgbyte.push_back(BYTE(pparams->allowedlossyerror));
@@ -370,7 +369,7 @@ JpegMarkerSegment* CreateLSE(const JlsCustomParameters* pcustom)
        push_back(rgbyte, (USHORT)pcustom->T2);
        push_back(rgbyte, (USHORT)pcustom->T3);
        push_back(rgbyte, (USHORT)pcustom->RESET);
-       
+
        return new JpegMarkerSegment(JPEG_LSE, rgbyte);
 }
 
@@ -395,7 +394,7 @@ void JLSInputStream::ReadPresetParameters()
                }
        }
 
-       
+
 }
 
 
@@ -412,7 +411,7 @@ void JLSInputStream::ReadStartOfScan()
        }
        _info.allowedlossyerror = ReadByte();
        _info.ilv = interleavemode(ReadByte());
-       
+
        if(_info.bytesperline == 0)
        {
                int width = _rect.Width != 0 ? _rect.Width : _info.width;
@@ -446,11 +445,11 @@ void JLSInputStream::ReadJfif()
        _info.jfif.units = ReadByte();
        _info.jfif.XDensity = ReadWord();
        _info.jfif.YDensity = ReadWord();
-       
+
        // thumbnail
        _info.jfif.Xthumb = ReadByte();
        _info.jfif.Ythumb = ReadByte();
-       if(_info.jfif.Xthumb > 0 && _info.jfif.pdataThumbnail) 
+       if(_info.jfif.Xthumb > 0 && _info.jfif.pdataThumbnail)
        {
                OFVector<char> tempbuff((char*)_info.jfif.pdataThumbnail, (char*)_info.jfif.pdataThumbnail+3*_info.jfif.Xthumb*_info.jfif.Ythumb);
                ReadNBytes(tempbuff, 3*_info.jfif.Xthumb*_info.jfif.Ythumb);
@@ -471,14 +470,14 @@ JpegMarkerSegment* CreateJFIF(const JfifParameters* jfif)
 
        push_back(rgbyte, (USHORT)jfif->Ver);
 
-       rgbyte.push_back(jfif->units);  
+       rgbyte.push_back(jfif->units);
        push_back(rgbyte, (USHORT)jfif->XDensity);
        push_back(rgbyte, (USHORT)jfif->YDensity);
 
        // thumbnail
        rgbyte.push_back((BYTE)jfif->Xthumb);
        rgbyte.push_back((BYTE)jfif->Ythumb);
-       if(jfif->Xthumb > 0) 
+       if(jfif->Xthumb > 0)
        {
                if(jfif->pdataThumbnail)
                        throw JlsException(InvalidJlsParameters);
@@ -486,7 +485,7 @@ JpegMarkerSegment* CreateJFIF(const JfifParameters* jfif)
                rgbyte.insert(rgbyte.end(), (BYTE*)jfif->pdataThumbnail, (BYTE*)jfif->pdataThumbnail+3*jfif->Xthumb*jfif->Ythumb
                );
        }
-       
+
        return new JpegMarkerSegment(JPEG_APP0, rgbyte);
 }
 
@@ -509,11 +508,11 @@ void JLSInputStream::ReadStartOfFrame()
 // ReadByte()
 //
 BYTE JLSInputStream::ReadByte()
-{  
+{
     if (_cbyteOffset >= _cbyteLength)
        throw JlsException(InvalidCompressedData);
 
-    return _pdata[_cbyteOffset++]; 
+    return _pdata[_cbyteOffset++];
 }
 
 
@@ -527,10 +526,10 @@ int JLSInputStream::ReadWord()
 }
 
 
-void JLSInputStream::ReadScan(void* pvout) 
+void JLSInputStream::ReadScan(void* pvout)
 {
        OFunique_ptr<DecoderStrategy> qcodec = JlsCodecFactory<DecoderStrategy>().GetCodec(_info, _info.custom);
-       
+
        BYTE **ptr = (BYTE **)&_pdata;
        size_t *size = &_cbyteLength;
        _cbyteOffset += qcodec->DecodeScan(pvout, _rect, ptr, size, _cbyteOffset, _bCompare);
@@ -549,9 +548,9 @@ public:
        }
 
        void Write(JLSOutputStream* pstream)
-       {               
+       {
                JlsParameters info = _info;
-               info.components = _ccompScan;   
+               info.components = _ccompScan;
                OFunique_ptr<EncoderStrategy> qcodec =JlsCodecFactory<EncoderStrategy>().GetCodec(info, _info.custom);
                size_t cbyteWritten = qcodec->EncodeScan((BYTE*)_pvoidRaw, pstream->get_pos(), pstream->get_size(), pstream->get_offset(), pstream->_bCompare);
                pstream->seek(cbyteWritten);
@@ -573,7 +572,7 @@ void JLSOutputStream::AddScan(const void* compareData, const JlsParameters* ppar
        }
        if (!IsDefault(&pparams->custom))
        {
-               _segments.push_back(CreateLSE(&pparams->custom));               
+               _segments.push_back(CreateLSE(&pparams->custom));
        }
        else if (pparams->bitspersample > 12)
        {
@@ -608,9 +607,9 @@ void JLSInputStream::ReadColorXForm()
 
        if(strncmp(&sourceTag[0],"mrfx", 4) != 0)
                return;
-       
+
        int xform = ReadByte();
-       switch(xform) 
+       switch(xform)
        {
                case COLORXFORM_NONE:
                case COLORXFORM_HP1:
@@ -625,4 +624,3 @@ void JLSInputStream::ReadColorXForm()
                        throw JlsException(InvalidCompressedData);
        }
 }
-
index c8fdaa901c477023e45465bac4882a860032dff9..3aa27fdc5bca6df9b067ec34cbe11c697b95e218 100644 (file)
@@ -10,7 +10,7 @@
 #include "dcmtk/ofstd/ofstd.h"    /* for size_t */
 #include "dcmtk/ofstd/ofdefine.h" /* for DCMTK_DECL_EXPORT */
 
-#ifdef charls_EXPORTS
+#ifdef dcmtkcharls_EXPORTS
 #define DCMTK_CHARLS_EXPORT DCMTK_DECL_EXPORT
 #else
 #define DCMTK_CHARLS_EXPORT DCMTK_DECL_IMPORT
index 314face74ba48929884af105eff8151ef453fcaa..bd928f8298df0ae56fee1f3804d5f2bacfa9828e 100644 (file)
@@ -4,4 +4,4 @@ include_directories("${dcmjpls_SOURCE_DIR}/include" "${ofstd_SOURCE_DIR}/include
 # create library from source files
 DCMTK_ADD_LIBRARY(dcmjpls djcparam djdecode djencode djrparam djcodecd djutils djcodece)
 
-DCMTK_TARGET_LINK_MODULES(dcmjpls ofstd oflog dcmdata dcmimgle dcmimage charls)
+DCMTK_TARGET_LINK_MODULES(dcmjpls ofstd oflog dcmdata dcmimgle dcmimage dcmtkcharls)
index 4b3b2390eaec285f5cf07ee10991d04b2a4e2bdb..fc0df5c7f2bf60730e80638aef3491fcbc292804 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2007-2019, OFFIS e.V.
+ *  Copyright (C) 2007-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -81,8 +81,16 @@ OFCondition DJLSDecoderBase::decode(
     DcmPixelSequence * pixSeq,
     DcmPolymorphOBOW& uncompressedPixelData,
     const DcmCodecParameter * cp,
-    const DcmStack& objStack) const
+    const DcmStack& objStack,
+    OFBool& removeOldRep) const
 {
+
+  // this codec may modify the DICOM header such that the previous pixel
+  // representation is not valid anymore, e.g. in the case of color images
+  // where the planar configuration can change. Indicate this to the caller
+  // to trigger removal.
+  removeOldRep = OFTrue;
+
   // retrieve pointer to dataset from parameter stack
   DcmStack localStack(objStack);
   (void)localStack.pop();  // pop pixel data element from stack
@@ -470,7 +478,8 @@ OFCondition DJLSDecoderBase::encode(
     const DcmRepresentationParameter * /* toRepParam */,
     DcmPixelSequence * & /* pixSeq */,
     const DcmCodecParameter * /* cp */,
-    DcmStack & /* objStack */) const
+    DcmStack & /* objStack */,
+    OFBool& /* removeOldRep */) const
 {
   // we are a decoder only
   return EC_IllegalCall;
@@ -484,7 +493,8 @@ OFCondition DJLSDecoderBase::encode(
     const DcmRepresentationParameter * /* toRepParam */,
     DcmPixelSequence * & /* toPixSeq */,
     const DcmCodecParameter * /* cp */,
-    DcmStack & /* objStack */) const
+    DcmStack & /* objStack */,
+    OFBool& /* removeOldRep */) const
 {
   // we don't support re-coding for now.
   return EC_IllegalCall;
index 1370fee7d5ea5975bf9172b24d55e44e291ac7dd..5e82662783eea2726e69c61c3caeff6d5a552786 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2007-2019, OFFIS e.V.
+ *  Copyright (C) 2007-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -108,7 +108,8 @@ OFCondition DJLSEncoderBase::decode(
     DcmPixelSequence * /* pixSeq */,
     DcmPolymorphOBOW& /* uncompressedPixelData */,
     const DcmCodecParameter * /* cp */,
-    const DcmStack& /* objStack */) const
+    const DcmStack& /* objStack */,
+    OFBool& /* removeOldRep */ ) const
 {
   // we are an encoder only
   return EC_IllegalCall;
@@ -138,7 +139,8 @@ OFCondition DJLSEncoderBase::encode(
     const DcmRepresentationParameter * /* toRepParam */,
     DcmPixelSequence * & /* toPixSeq */,
     const DcmCodecParameter * /* cp */,
-    DcmStack & /* objStack */) const
+    DcmStack& /* objStack */,
+    OFBool& /* removeOldRep */ ) const
 {
   // we don't support re-coding for now.
   return EC_IllegalCall;
@@ -150,11 +152,17 @@ OFCondition DJLSEncoderBase::encode(
     const DcmRepresentationParameter * toRepParam,
     DcmPixelSequence * & pixSeq,
     const DcmCodecParameter *cp,
-    DcmStack & objStack) const
+    DcmStack& objStack,
+    OFBool& removeOldRep) const
 {
   OFCondition result = EC_Normal;
   DJLSRepresentationParameter defRep;
 
+  // this codec may modify the DICOM header such that the previous pixel
+  // representation is not valid anymore. Indicate this to the caller
+  // to trigger removal.
+  removeOldRep = OFTrue;
+
   // retrieve pointer to dataset from parameter stack
   DcmStack localStack(objStack);
   (void)localStack.pop();  // pop pixel data element from stack
@@ -685,14 +693,20 @@ OFCondition DJLSEncoderBase::compressRawFrame(
     case DJLSCodecParameter::interleaveLine:
       jls_params.ilv = ILV_LINE;
       break;
+#ifdef ENABLE_DCMJPLS_INTERLEAVE_NONE
     case DJLSCodecParameter::interleaveNone:
       jls_params.ilv = ILV_NONE;
       break;
+#endif
     case DJLSCodecParameter::interleaveDefault:
     default:
       // In default mode we just never convert the image to another
       // interleave-mode. Instead, we use what is already there.
+#ifdef ENABLE_DCMJPLS_INTERLEAVE_NONE
       jls_params.ilv = ilv;
+#else
+      jls_params.ilv = (ilv == ILV_NONE ? ILV_LINE : ilv);
+#endif
       break;
   }
 
@@ -1099,9 +1113,11 @@ OFCondition DJLSEncoderBase::compressCookedFrame(
     case DJLSCodecParameter::interleaveLine:
       jls_params.ilv = ILV_LINE;
       break;
+#ifdef ENABLE_DCMJPLS_INTERLEAVE_NONE
     case DJLSCodecParameter::interleaveNone:
       jls_params.ilv = ILV_NONE;
       break;
+#endif
     case DJLSCodecParameter::interleaveDefault:
     default:
       // Default for the cooked encoder is always ILV_LINE
@@ -1117,6 +1133,8 @@ OFCondition DJLSEncoderBase::compressCookedFrame(
 
   Uint8 *frameBuffer = NULL;
   Uint8 *framePointer = buffer;
+
+#ifdef ENABLE_DCMJPLS_INTERLEAVE_NONE
   // Do we have to convert the image to color-by-plane now?
   if (jls_params.ilv == ILV_NONE && jls_params.components != 1)
   {
@@ -1126,6 +1144,7 @@ OFCondition DJLSEncoderBase::compressCookedFrame(
     framePointer = frameBuffer;
     result = convertToUninterleaved(frameBuffer, buffer, samplesPerPixel, width, height, jls_params.bitspersample);
   }
+#endif
 
   size_t compressed_buffer_size = buffer_size + 1024;
   BYTE *compressed_buffer = new BYTE[compressed_buffer_size];
index aa0ff8b250c17949eadbde008002ad695ae4da0f..6ab669f207d4268d29b51ea5379046b01e1c8b5d 100644 (file)
@@ -29,7 +29,7 @@ endif()
 foreach(PROGRAM dcmrecv dcmsend echoscu findscu getscu movescu storescp storescu termscu)
   DCMTK_TARGET_LINK_MODULES(${PROGRAM} dcmnet dcmdata oflog ofstd)
 endforeach()
-foreach(PROGRAM echoscu findscu storescp storescu)
+foreach(PROGRAM dcmrecv echoscu findscu storescp storescu)
   DCMTK_TARGET_LINK_MODULES(${PROGRAM} dcmtls)
 endforeach()
 
index 4f10a0254f4ed5d21e58a9ad167e1c390816a395..167ad9d0bf826033d6f6624d90b5dd674b5fc31c 100644 (file)
@@ -27,6 +27,8 @@ dcmrecv.o: dcmrecv.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
  ../include/dcmtk/dcmnet/dstorscp.h \
  ../../ofstd/include/dcmtk/ofstd/offname.h ../include/dcmtk/dcmnet/scp.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
@@ -51,8 +53,6 @@ dcmrecv.o: dcmrecv.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
@@ -125,12 +125,12 @@ dcmrecv.o: dcmrecv.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofbmanip.h ../include/dcmtk/dcmnet/lst.h \
  ../include/dcmtk/dcmnet/dul.h ../include/dcmtk/dcmnet/extneg.h \
  ../include/dcmtk/dcmnet/dcuserid.h ../include/dcmtk/dcmnet/dntypes.h \
- ../include/dcmtk/dcmnet/dimse.h ../include/dcmtk/dcmnet/scpcfg.h \
- ../include/dcmtk/dcmnet/dcasccff.h ../include/dcmtk/dcmnet/dcasccfg.h \
- ../include/dcmtk/dcmnet/dccftsmp.h ../include/dcmtk/dcmnet/dccfuidh.h \
- ../include/dcmtk/dcmnet/dccfpcmp.h ../include/dcmtk/dcmnet/dccfrsmp.h \
- ../include/dcmtk/dcmnet/dccfenmp.h ../include/dcmtk/dcmnet/dccfprmp.h \
- ../include/dcmtk/dcmnet/diutil.h
+ ../include/dcmtk/dcmnet/dimse.h ../include/dcmtk/dcmnet/diutil.h \
+ ../include/dcmtk/dcmnet/scpcfg.h ../include/dcmtk/dcmnet/dcasccff.h \
+ ../include/dcmtk/dcmnet/dcasccfg.h ../include/dcmtk/dcmnet/dccftsmp.h \
+ ../include/dcmtk/dcmnet/dccfuidh.h ../include/dcmtk/dcmnet/dccfpcmp.h \
+ ../include/dcmtk/dcmnet/dccfrsmp.h ../include/dcmtk/dcmnet/dccfenmp.h \
+ ../include/dcmtk/dcmnet/dccfprmp.h
 dcmsend.o: dcmsend.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
@@ -252,17 +252,17 @@ dcmsend.o: dcmsend.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
- ../include/dcmtk/dcmnet/dcompat.h \
- ../../ofstd/include/dcmtk/ofstd/ofbmanip.h \
- ../include/dcmtk/dcmnet/dndefine.h ../include/dcmtk/dcmnet/dimse.h \
+ ../include/dcmtk/dcmnet/dcasccff.h ../include/dcmtk/dcmnet/dndefine.h \
+ ../include/dcmtk/dcmnet/dcasccfg.h ../include/dcmtk/dcmnet/assoc.h \
  ../include/dcmtk/dcmnet/dicom.h ../include/dcmtk/dcmnet/cond.h \
- ../include/dcmtk/dcmnet/lst.h ../include/dcmtk/dcmnet/dul.h \
- ../include/dcmtk/dcmnet/extneg.h ../include/dcmtk/dcmnet/dcuserid.h \
- ../include/dcmtk/dcmnet/dntypes.h ../include/dcmtk/dcmnet/assoc.h \
- ../include/dcmtk/dcmnet/dcasccff.h ../include/dcmtk/dcmnet/dcasccfg.h \
+ ../include/dcmtk/dcmnet/dcompat.h \
+ ../../ofstd/include/dcmtk/ofstd/ofbmanip.h ../include/dcmtk/dcmnet/lst.h \
+ ../include/dcmtk/dcmnet/dul.h ../include/dcmtk/dcmnet/extneg.h \
+ ../include/dcmtk/dcmnet/dcuserid.h ../include/dcmtk/dcmnet/dntypes.h \
  ../include/dcmtk/dcmnet/dccftsmp.h ../include/dcmtk/dcmnet/dccfuidh.h \
  ../include/dcmtk/dcmnet/dccfpcmp.h ../include/dcmtk/dcmnet/dccfrsmp.h \
  ../include/dcmtk/dcmnet/dccfenmp.h ../include/dcmtk/dcmnet/dccfprmp.h \
+ ../include/dcmtk/dcmnet/dimse.h \
  ../../dcmjpeg/include/dcmtk/dcmjpeg/djdecode.h \
  ../../dcmjpeg/include/dcmtk/dcmjpeg/djutils.h \
  ../../dcmimgle/include/dcmtk/dcmimgle/diutils.h \
@@ -553,17 +553,17 @@ getscu.o: getscu.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmnet/dcompat.h \
- ../../ofstd/include/dcmtk/ofstd/ofbmanip.h \
- ../include/dcmtk/dcmnet/dndefine.h ../include/dcmtk/dcmnet/dimse.h \
+ ../include/dcmtk/dcmnet/dcasccff.h ../include/dcmtk/dcmnet/dndefine.h \
+ ../include/dcmtk/dcmnet/dcasccfg.h ../include/dcmtk/dcmnet/assoc.h \
  ../include/dcmtk/dcmnet/dicom.h ../include/dcmtk/dcmnet/cond.h \
- ../include/dcmtk/dcmnet/lst.h ../include/dcmtk/dcmnet/dul.h \
- ../include/dcmtk/dcmnet/extneg.h ../include/dcmtk/dcmnet/dcuserid.h \
- ../include/dcmtk/dcmnet/dntypes.h ../include/dcmtk/dcmnet/assoc.h \
- ../include/dcmtk/dcmnet/dcasccff.h ../include/dcmtk/dcmnet/dcasccfg.h \
+ ../include/dcmtk/dcmnet/dcompat.h \
+ ../../ofstd/include/dcmtk/ofstd/ofbmanip.h ../include/dcmtk/dcmnet/lst.h \
+ ../include/dcmtk/dcmnet/dul.h ../include/dcmtk/dcmnet/extneg.h \
+ ../include/dcmtk/dcmnet/dcuserid.h ../include/dcmtk/dcmnet/dntypes.h \
  ../include/dcmtk/dcmnet/dccftsmp.h ../include/dcmtk/dcmnet/dccfuidh.h \
  ../include/dcmtk/dcmnet/dccfpcmp.h ../include/dcmtk/dcmnet/dccfrsmp.h \
  ../include/dcmtk/dcmnet/dccfenmp.h ../include/dcmtk/dcmnet/dccfprmp.h \
+ ../include/dcmtk/dcmnet/dimse.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrmz.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpath.h
 movescu.o: movescu.cc ../../config/include/dcmtk/config/osconfig.h \
index 765e1dd10931795d002b9f19011b27a907c23a22..625c39c0502e8ff0776035bc0918936d9622bae0 100644 (file)
@@ -32,7 +32,7 @@ LIBDIRS = -L$(top_srcdir)/libsrc -L$(ofstddir)/libsrc -L$(oflogdir)/libsrc \
 LOCALLIBS = -ldcmnet -ldcmdata -loflog -lofstd $(ZLIBLIBS) $(TCPWRAPPERLIBS) \
        $(CHARCONVLIBS) $(MATHLIBS)
 DCMTLSLIBS = -ldcmtls
-COMPR_LIBS = -ldcmjpls -lcharls -ldcmjpeg -lijg8 -lijg12 -lijg16 -ldcmimage -ldcmimgle
+COMPR_LIBS = -ldcmjpls -ldcmtkcharls -ldcmjpeg -lijg8 -lijg12 -lijg16 -ldcmimage -ldcmimgle
 
 objs = echoscu.o storescu.o storescp.o findscu.o movescu.o termscu.o getscu.o dcmsend.o \
        dcmrecv.o
@@ -68,7 +68,7 @@ dcmsend: dcmsend.o
        $(CXX) $(CXXFLAGS) $(LIBDIRS) $(LDFLAGS) -o $@ $@.o $(COMPR_LIBS) $(LOCALLIBS) $(TIFFLIBS) $(PNGLIBS) $(LIBS)
 
 dcmrecv: dcmrecv.o
-       $(CXX) $(CXXFLAGS) $(LIBDIRS) $(LDFLAGS) -o $@ $@.o $(LOCALLIBS) $(LIBS)
+       $(CXX) $(CXXFLAGS) $(LIBDIRS) $(LDFLAGS) -o $@ $@.o $(LOCALLIBS) $(DCMTLSLIBS) $(OPENSSLLIBS) $(LIBS)
 
 install: all
        $(configdir)/mkinstalldirs $(DESTDIR)$(bindir)
index 408581f80c91a8b7c1f245465995aa07a439e869..1e400019b44cdfcaf15e17c76a1f4b60403d9b17 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2013-2018, OFFIS e.V.
+ *  Copyright (C) 2013-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -29,6 +29,7 @@
 #include "dcmtk/dcmdata/dcuid.h"     /* for dcmtk version name */
 #include "dcmtk/dcmdata/cmdlnarg.h"  /* for prepareCmdLineArgs */
 #include "dcmtk/dcmnet/dstorscp.h"   /* for DcmStorageSCP */
+#include "dcmtk/dcmtls/tlsopt.h"     /* for DcmTLSOptions */
 
 
 /* general definitions */
@@ -51,6 +52,7 @@ static char rcsid[] = "$dcmtk: " OFFIS_CONSOLE_APPLICATION " v"
 #define EXITCODE_CANNOT_INITIALIZE_NETWORK       60      // placeholder, currently not used
 #define EXITCODE_CANNOT_START_SCP_AND_LISTEN     64
 #define EXITCODE_INVALID_ASSOCIATION_CONFIG      66
+#define EXITCODE_CANNOT_CREATE_TRANSPORT_LAYER   71
 
 
 /* helper macro for converting stream output to a string */
@@ -68,7 +70,13 @@ static char rcsid[] = "$dcmtk: " OFFIS_CONSOLE_APPLICATION " v"
 
 int main(int argc, char *argv[])
 {
+
+#ifdef WITH_OPENSSL
+    DcmTLSTransportLayer::initializeOpenSSL();
+#endif
+
     OFOStringStream optStream;
+    DcmTLSOptions tlsOptions(NET_ACCEPTOR);
 
     const char *opt_configFile = NULL;
     const char *opt_profileName = NULL;
@@ -122,6 +130,10 @@ int main(int argc, char *argv[])
         cmd.addOption("--max-pdu",             "-pdu", 1, optString3.c_str(),
                                                           optString4.c_str());
         cmd.addOption("--disable-host-lookup", "-dhl",    "disable hostname lookup");
+
+    /* add TLS specific command line options if (and only if) we are compiling with OpenSSL */
+    tlsOptions.addTLSCommandlineOptions(cmd);
+
     cmd.addGroup("output options:");
       cmd.addSubGroup("general:");
         CONVERT_TO_STRING("[d]irectory: string (default: \"" << opt_outputDirectory << "\")", optString5);
@@ -152,9 +164,23 @@ int main(int argc, char *argv[])
             if (cmd.findOption("--version"))
             {
                 app.printHeader(OFTrue /*print host identifier*/);
-                COUT << OFendl << "External libraries used: none" << OFendl;
+                COUT << OFendl << "External libraries used:";
+#ifdef WITH_OPENSSL
+                COUT << OFendl;
+                tlsOptions.printLibraryVersion();
+#else
+                COUT << " none" << OFendl;
+#endif
                 return EXITCODE_NO_ERROR;
             }
+
+            /* check if the command line contains the --list-ciphers option */
+            if (tlsOptions.listOfCiphersRequested(cmd))
+            {
+                tlsOptions.printSupportedCiphersuites(app, COUT);
+                return EXITCODE_NO_ERROR;
+            }
+
         }
 
         /* general options */
@@ -233,6 +259,9 @@ int main(int argc, char *argv[])
 
         /* command line parameters */
         app.checkParam(cmd.getParamAndCheckMinMax(1, opt_port, 1, 65535));
+
+        /* evaluate (most of) the TLS command line options (if we are compiling with OpenSSL) */
+        tlsOptions.parseArguments(app, cmd);
     }
 
     /* print resource identifier */
@@ -290,6 +319,18 @@ int main(int argc, char *argv[])
 
     OFLOG_INFO(dcmrecvLogger, "starting service class provider and listening ...");
 
+    /* create a secure transport layer if requested and OpenSSL is available */
+    status = tlsOptions.createTransportLayer(NULL, NULL, app, cmd);
+    if (status.bad())
+    {
+        OFString tempStr;
+        OFLOG_FATAL(dcmrecvLogger, DimseCondition::dump(tempStr, status));
+        return EXITCODE_CANNOT_CREATE_TRANSPORT_LAYER;
+    }
+
+    if (tlsOptions.secureConnectionRequested())
+        storageSCP.getConfig().setTransportLayer(tlsOptions.getTransportLayer());
+
     /* start SCP and listen on the specified port */
     status = storageSCP.listen();
     if (status.bad())
index fcd9e965108e9fe96c548518caa7c387c003b6f6..da3e5d0abbfa0c75dd37b7859613c0361e3fbad3 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -23,6 +23,7 @@
 
 #include "dcmtk/dcmnet/dfindscu.h"
 #include "dcmtk/dcmnet/diutil.h"
+#include "dcmtk/dcmnet/dcmtrans.h"    /* for dcmSocketSend/ReceiveTimeout */
 #include "dcmtk/dcmdata/cmdlnarg.h"
 #include "dcmtk/ofstd/ofconapp.h"
 #include "dcmtk/dcmdata/dcdict.h"
@@ -47,15 +48,24 @@ static char rcsid[] = "$dcmtk: " OFFIS_CONSOLE_APPLICATION " v"
 #define APPLICATIONTITLE        "FINDSCU"
 #define PEERAPPLICATIONTITLE    "ANY-SCP"
 
+/* helper macro for converting stream output to a string */
+#define CONVERT_TO_STRING(output, string) \
+    optStream.str(""); \
+    optStream.clear(); \
+    optStream << output << OFStringStream_ends; \
+    OFSTRINGSTREAM_GETOFSTRING(optStream, string)
+
 #define SHORTCOL 4
 #define LONGCOL 20
 
 int main(int argc, char *argv[])
 {
+    OFOStringStream       optStream;
     OFList<OFString>      fileNameList;
     OFBool                opt_abortAssociation = OFFalse;
     const char *          opt_abstractSyntax = UID_FINDModalityWorklistInformationModel;
     int                   opt_acse_timeout = 30;
+    OFCmdSignedInt        opt_socket_timeout = 60;
     T_DIMSE_BlockingMode  opt_blockMode = DIMSE_BLOCKING;
     OFCmdSignedInt        opt_cancelAfterNResponses = -1;
     int                   opt_dimse_timeout = 0;
@@ -63,6 +73,7 @@ int main(int argc, char *argv[])
     DcmFindSCUExtractMode opt_extractResponses = FEM_none;
     OFString              opt_extractXMLFilename;
     OFString              opt_outputDirectory = ".";
+    OFCmdUnsignedInt      opt_limitOutputToNResponses = 0;
     OFCmdUnsignedInt      opt_maxReceivePDULength = ASC_DEFAULTMAXPDU;
     E_TransferSyntax      opt_networkTransferSyntax = EXS_Unknown;
     const char *          opt_ourTitle = APPLICATIONTITLE;
@@ -88,7 +99,6 @@ int main(int argc, char *argv[])
   DcmTLSTransportLayer::initializeOpenSSL();
 #endif
 
-  char tempstr[20];
   OFString temp_str;
   OFConsoleApplication app(OFFIS_CONSOLE_APPLICATION , "DICOM query (C-FIND) SCU", rcsid);
   OFCommandLine cmd;
@@ -114,14 +124,8 @@ int main(int argc, char *argv[])
       cmd.addOption("--study",              "-S",      "use study root information model");
       cmd.addOption("--psonly",             "-O",      "use patient/study only information model");
     cmd.addSubGroup("application entity titles:");
-      OFString opt1 = "set my calling AE title (default: ";
-      opt1 += APPLICATIONTITLE;
-      opt1 += ")";
-      cmd.addOption("--aetitle",            "-aet", 1, "[a]etitle: string", opt1.c_str());
-      OFString opt2 = "set called AE title of peer (default: ";
-      opt2 += PEERAPPLICATIONTITLE;
-      opt2 += ")";
-      cmd.addOption("--call",               "-aec", 1, "[a]etitle: string", opt2.c_str());
+      cmd.addOption("--aetitle",            "-aet", 1, "[a]etitle: string", "set my calling AE title (default: " APPLICATIONTITLE ")");
+      cmd.addOption("--call",               "-aec", 1, "[a]etitle: string", "set called AE title of peer (default: " PEERAPPLICATIONTITLE ")");
     cmd.addSubGroup("post-1993 value representations:");
       cmd.addOption("--enable-new-vr",      "+u",      "enable support for new VRs (UN/UT) (default)");
       cmd.addOption("--disable-new-vr",     "-u",      "disable support for new VRs, convert to OB");
@@ -139,21 +143,15 @@ int main(int argc, char *argv[])
                                                        "0=uncompressed, 1=fastest, 9=best compression");
 #endif
     cmd.addSubGroup("other network options:");
-      OFString opt3 = "set max receive pdu to n bytes (default: ";
-      sprintf(tempstr, "%ld", OFstatic_cast(long, ASC_DEFAULTMAXPDU));
-      opt3 += tempstr;
-      opt3 += ")";
-      OFString opt4 = "[n]umber of bytes: integer (";
-      sprintf(tempstr, "%ld", OFstatic_cast(long, ASC_MINIMUMPDUSIZE));
-      opt4 += tempstr;
-      opt4 += "..";
-      sprintf(tempstr, "%ld", OFstatic_cast(long, ASC_MAXIMUMPDUSIZE));
-      opt4 += tempstr;
-      opt4 += ")";
       cmd.addOption("--timeout",            "-to",  1, "[s]econds: integer (default: unlimited)", "timeout for connection requests");
-      cmd.addOption("--acse-timeout",       "-ta",  1, "[s]econds: integer (default: 30)", "timeout for ACSE messages");
+      CONVERT_TO_STRING("[s]econds: integer (default: " << opt_socket_timeout << ")", optString1);
+      cmd.addOption("--socket-timeout",     "-ts",  1, optString1.c_str(), "timeout for network socket (0 for none)");
+      CONVERT_TO_STRING("[s]econds: integer (default: " << opt_acse_timeout << ")", optString2);
+      cmd.addOption("--acse-timeout",       "-ta",  1, optString2.c_str(), "timeout for ACSE messages");
       cmd.addOption("--dimse-timeout",      "-td",  1, "[s]econds: integer (default: unlimited)", "timeout for DIMSE messages");
-      cmd.addOption("--max-pdu",            "-pdu", 1, opt4.c_str(), opt3.c_str());
+      CONVERT_TO_STRING("[n]umber of bytes: integer (" << ASC_MINIMUMPDUSIZE << ".." << ASC_MAXIMUMPDUSIZE << ")", optString3);
+      CONVERT_TO_STRING("set max receive pdu to n bytes (default: " << opt_maxReceivePDULength << ")", optString4);
+      cmd.addOption("--max-pdu",            "-pdu", 1, optString3.c_str(), optString4.c_str());
       cmd.addOption("--repeat",                     1, "[n]umber: integer", "repeat n times");
       cmd.addOption("--abort",                         "abort association instead of releasing it");
       cmd.addOption("--cancel",                     1, "[n]umber: integer",
@@ -176,6 +174,8 @@ int main(int argc, char *argv[])
       cmd.addOption("--extract-xml",        "-Xx",     "extract responses to XML file (rsp0001.xml...)");
       cmd.addOption("--extract-xml-single", "-Xs",  1, "[f]ilename: string",
                                                        "extract all responses to given XML file f");
+      cmd.addOption("--limit-output",       "-Xlo", 1, "[n]umber: integer",
+                                                       "limit number of responses extracted to file to n\n(default: unlimited)");
 
     /* evaluate command line */
     prepareCmdLineArgs(argc, argv, OFFIS_CONSOLE_APPLICATION);
@@ -269,6 +269,12 @@ int main(int argc, char *argv[])
         dcmConnectionTimeout.set(OFstatic_cast(Sint32, opt_timeout));
       }
 
+      if (cmd.findOption("--socket-timeout"))
+        app.checkValue(cmd.getValueAndCheckMin(opt_socket_timeout, -1));
+      // always set the timeout values since the global default might be different
+      dcmSocketSendTimeout.set(OFstatic_cast(Sint32, opt_socket_timeout));
+      dcmSocketReceiveTimeout.set(OFstatic_cast(Sint32, opt_socket_timeout));
+
       if (cmd.findOption("--acse-timeout"))
       {
         OFCmdSignedInt opt_timeout = 0;
@@ -310,6 +316,11 @@ int main(int argc, char *argv[])
           app.checkValue(cmd.getValue(opt_extractXMLFilename));
       }
       cmd.endOptionBlock();
+      if (cmd.findOption("--limit-output"))
+      {
+          app.checkDependence("--limit-output", "--extract, --extract-xml or --extract-xml-single", opt_extractResponses != FEM_none);
+          app.checkValue(cmd.getValueAndCheckMin(opt_limitOutputToNResponses, 1));
+      }
 
       /* finally parse filenames */
       int paramCount = cmd.getParamCount();
@@ -420,6 +431,9 @@ int main(int argc, char *argv[])
     }
 #endif
 
+    // set further parameters
+    findscu.setOutputResponseLimit(opt_limitOutputToNResponses);
+
     // do the main work: negotiate network association, perform C-FIND transaction,
     // process results, and finally tear down the association.
     cond = findscu.performQuery(
index 7c406046557768286a2ab0a6f8ac7b3c53c2744c..eadbcc429d49f799b764d18db91423057bb389e4 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2018, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -1374,7 +1374,7 @@ storeSCPCallback(
 
          OFCondition cond = cbdata->dcmff->saveFile(ofname.c_str(), xfer, opt_sequenceType, opt_groupLength,
            opt_paddingType, OFstatic_cast(Uint32, opt_filepad), OFstatic_cast(Uint32, opt_itempad),
-           (opt_useMetaheader) ? EWM_fileformat : EWM_dataset);
+           (opt_useMetaheader) ? EWM_createNewMeta : EWM_dataset);
          if (cond.bad())
          {
            OFLOG_ERROR(movescuLogger, "cannot write DICOM file: " << ofname);
index db289225a2b342521d0c3e41790d52ec141c0965..78ff9608cdabecd526a62631e1a6363f15d92faf 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -147,11 +147,8 @@ OFBool             opt_promiscuous = OFFalse;
 OFBool             opt_correctUIDPadding = OFFalse;
 OFBool             opt_inetd_mode = OFFalse;
 OFString           callingAETitle;                    // calling application entity title will be stored here
-OFString           lastCallingAETitle;
 OFString           calledAETitle;                     // called application entity title will be stored here
-OFString           lastCalledAETitle;
 OFString           callingPresentationAddress;        // remote hostname or IP address will be stored here
-OFString           lastCallingPresentationAddress;
 const char *       opt_respondingAETitle = APPLICATIONTITLE;
 static OFString    opt_outputDirectory = ".";         // default: output directory equals "."
 E_SortStudyMode    opt_sortStudyMode = ESM_None;      // default: no sorting
@@ -343,6 +340,9 @@ int main(int argc, char *argv[])
       cmd.addOption("--padding-off",            "-p",      "no padding (default)");
       cmd.addOption("--padding-create",         "+p",   2, "[f]ile-pad [i]tem-pad: integer",
                                                            "align file on multiple of f bytes and items\non multiple of i bytes");
+    cmd.addSubGroup("handling of defined length UN elements:");
+      cmd.addOption("--retain-un",              "-uc",     "retain elements as UN (default)");
+      cmd.addOption("--convert-un",             "+uc",     "convert to real VR if known");
 #ifdef WITH_ZLIB
     cmd.addSubGroup("deflate compression level (only with --write-xfer-deflated/same):");
       cmd.addOption("--compression-level",      "+cl",  1, "[l]evel: integer (default: 6)",
@@ -354,7 +354,6 @@ int main(int argc, char *argv[])
       cmd.addOption("--sort-on-study-uid",      "-su",  1, "[p]refix: string",
                                                            "sort studies using prefix p and the Study\nInstance UID");
       cmd.addOption("--sort-on-patientname",    "-sp",     "sort studies using the Patient's Name and\na timestamp");
-
     cmd.addSubGroup("filename generation:");
       cmd.addOption("--default-filenames",      "-uf",     "generate filename from instance UID (default)");
       cmd.addOption("--unique-filenames",       "+uf",     "generate unique filenames");
@@ -789,6 +788,11 @@ int main(int argc, char *argv[])
     }
     cmd.endOptionBlock();
 
+    cmd.beginOptionBlock();
+    if (cmd.findOption("--retain-un")) dcmEnableUnknownVRConversion.set(OFFalse);
+    if (cmd.findOption("--convert-un")) dcmEnableUnknownVRConversion.set(OFTrue);
+    cmd.endOptionBlock();
+
 #ifdef WITH_ZLIB
     if (cmd.findOption("--compression-level"))
     {
@@ -1453,10 +1457,6 @@ static OFCondition acceptAssociation(T_ASC_Network *net, DcmAssociationConfigura
   }
 #endif
 
-  // store previous values for later use
-  lastCallingAETitle = callingAETitle;
-  lastCalledAETitle = calledAETitle;
-  lastCallingPresentationAddress = callingPresentationAddress;
   // store calling and called aetitle in global variables to enable
   // the --exec options using them. Enclose in quotation marks because
   // aetitles may contain space characters.
@@ -2323,13 +2323,13 @@ static void executeOnEndOfStudy()
   cmd = replaceChars( cmd, OFString(PATH_PLACEHOLDER), lastStudySubdirectoryPathAndName );
 
   // perform substitution for placeholder #a
-  cmd = replaceChars( cmd, OFString(CALLING_AETITLE_PLACEHOLDER), (endOfStudyThroughTimeoutEvent) ? callingAETitle : lastCallingAETitle );
+  cmd = replaceChars( cmd, OFString(CALLING_AETITLE_PLACEHOLDER), callingAETitle );
 
   // perform substitution for placeholder #c
-  cmd = replaceChars( cmd, OFString(CALLED_AETITLE_PLACEHOLDER), (endOfStudyThroughTimeoutEvent) ? calledAETitle : lastCalledAETitle );
+  cmd = replaceChars( cmd, OFString(CALLED_AETITLE_PLACEHOLDER), calledAETitle );
 
   // perform substitution for placeholder #r
-  cmd = replaceChars( cmd, OFString(CALLING_PRESENTATION_ADDRESS_PLACEHOLDER), (endOfStudyThroughTimeoutEvent) ? callingPresentationAddress : lastCallingPresentationAddress );
+  cmd = replaceChars( cmd, OFString(CALLING_PRESENTATION_ADDRESS_PLACEHOLDER), callingPresentationAddress );
 
   // Execute command in a new process
   executeCommand( cmd );
@@ -2401,13 +2401,13 @@ static void executeCommand( const OFString &cmd )
   }
 #else
   PROCESS_INFORMATION procinfo;
-  STARTUPINFO sinfo;
+  STARTUPINFOA sinfo;
   OFBitmanipTemplate<char>::zeroMem((char *)&sinfo, sizeof(sinfo));
   sinfo.cb = sizeof(sinfo);
 
   // execute command (Attention: Do not pass DETACHED_PROCESS as sixth argument to the below
   // called function because in such a case the execution of batch-files is not going to work.)
-  if( !CreateProcess(NULL, OFconst_cast(char *, cmd.c_str()), NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo) )
+  if( !CreateProcessA(NULL, OFconst_cast(char *, cmd.c_str()), NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo) )
     OFLOG_ERROR(storescpLogger, "cannot execute command '" << cmd << "'");
 
   if (opt_execSync)
index ed437bfb821bbb76bc6329de76b5dd9f9c7bb805..b36f34b05c9e0a35a82b506a64431cfcf0fa9184 100644 (file)
@@ -90,6 +90,98 @@ other network options:
   -dhl  --disable-host-lookup  disable hostname lookup
 \endverbatim
 
+\subsection dcmrecv_tls_options transport layer security (TLS) options
+\verbatim
+transport protocol stack:
+
+  -tls  --disable-tls
+          use normal TCP/IP connection (default)
+
+  +tls  --enable-tls  [p]rivate key file, [c]ertificate file: string
+          use authenticated secure TLS connection
+
+private key password (only with --enable-tls):
+
+  +ps   --std-passwd
+          prompt user to type password on stdin (default)
+
+  +pw   --use-passwd  [p]assword: string
+          use specified password
+
+  -pw   --null-passwd
+          use empty string as password
+
+key and certificate file format:
+
+  -pem  --pem-keys
+          read keys and certificates as PEM file (default)
+
+  -der  --der-keys
+          read keys and certificates as DER file
+
+certification authority:
+
+  +cf   --add-cert-file  [f]ilename: string
+          add certificate file to list of certificates
+
+  +cd   --add-cert-dir  [d]irectory: string
+          add certificates in d to list of certificates
+
+security profile:
+
+  +px   --profile-bcp195
+          BCP 195 TLS Profile (default)
+
+  +py   --profile-bcp195-nd
+          Non-downgrading BCP 195 TLS Profile
+
+  +pz   --profile-bcp195-ex
+          Extended BCP 195 TLS Profile
+
+  +pb   --profile-basic
+          Basic TLS Secure Transport Connection Profile (retired)
+
+  +pa   --profile-aes
+          AES TLS Secure Transport Connection Profile (retired)
+
+  +pn   --profile-null
+          Authenticated unencrypted communication
+          (retired, was used in IHE ATNA)
+
+ciphersuite:
+
+  +cc   --list-ciphers
+          show list of supported TLS ciphersuites and exit
+
+  +cs   --cipher  [c]iphersuite name: string
+          add ciphersuite to list of negotiated suites
+
+  +dp   --dhparam  [f]ilename: string
+          read DH parameters for DH/DSS ciphersuites
+
+pseudo random generator:
+
+  +rs   --seed  [f]ilename: string
+          seed random generator with contents of f
+
+  +ws   --write-seed
+          write back modified seed (only with --seed)
+
+  +wf   --write-seed-file  [f]ilename: string (only with --seed)
+          write modified seed to file f
+
+peer authentication:
+
+  -rc   --require-peer-cert
+          verify peer certificate, fail if absent (default)
+
+  -vc   --verify-peer-cert
+          verify peer certificate if present
+
+  -ic   --ignore-peer-cert
+          don't verify peer certificate
+\endverbatim
+
 \subsection dcmrecv_output_options output options
 \verbatim
 general:
@@ -323,6 +415,7 @@ EXITCODE_INVALID_OUTPUT_DIRECTORY        45
 EXITCODE_CANNOT_INITIALIZE_NETWORK       60 (*)
 EXITCODE_CANNOT_START_SCP_AND_LISTEN     64
 EXITCODE_INVALID_ASSOCIATION_CONFIG      66
+EXITCODE_CANNOT_CREATE_TRANSPORT_LAYER   71
 \endverbatim
 
 (*) Actually, these codes are currently not used by \b dcmrecv but serve as a
@@ -355,6 +448,6 @@ It is an error if no data dictionary can be loaded.
 
 \section dcmrecv_copyright COPYRIGHT
 
-Copyright (C) 2013-2017 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 2013-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index 66ef9c225ebb9c742cd8ba423d6ccd33fef232f9..ec45178514c92f0634edc87193e3c8dd4aaef79e 100644 (file)
@@ -133,10 +133,10 @@ key and certificate file format:
 
 certification authority:
 
-  +cf   --add-cert-file  [c]ertificate filename: string
+  +cf   --add-cert-file  [f]ilename: string
           add certificate file to list of certificates
 
-  +cd   --add-cert-dir  [c]ertificate directory: string
+  +cd   --add-cert-dir  [d]irectory: string
           add certificates in d to list of certificates
 
 security profile:
@@ -294,6 +294,6 @@ It is an error if no data dictionary can be loaded.
 
 \section echoscu_copyright COPYRIGHT
 
-Copyright (C) 1994-2018 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 1994-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index 74e9a0079fde3d8deab9c8ea73423dcc771fda6c..2b717449419d64d2cab7622d514f223da8a82f75 100644 (file)
@@ -128,6 +128,9 @@ other network options:
   -to   --timeout  [s]econds: integer (default: unlimited)
           timeout for connection requests
 
+  -ts   --socket-timeout  [s]econds: integer (default: 60)
+          timeout for network socket (0 for none)
+
   -ta   --acse-timeout  [s]econds: integer (default: 30)
           timeout for ACSE messages
 
@@ -181,10 +184,10 @@ key and certificate file format:
 
 certification authority:
 
-  +cf   --add-cert-file  [c]ertificate filename: string
+  +cf   --add-cert-file  [f]ilename: string
           add certificate file to list of certificates
 
-  +cd   --add-cert-dir  [c]ertificate directory: string
+  +cd   --add-cert-dir  [d]irectory: string
           add certificates in d to list of certificates
 
 security profile:
@@ -267,6 +270,10 @@ C-FIND responses:
 
   -Xs   --extract-xml-single  [f]ilename: string
           extract all responses to given XML file f
+
+  -Xlo  --limit-output  [n]umber: integer
+          limit number of responses extracted to file to n
+          (default: unlimited)
 \endverbatim
 
 \section findscu_notes NOTES
@@ -448,6 +455,6 @@ It is an error if no data dictionary can be loaded.
 
 \section findscu_copyright COPYRIGHT
 
-Copyright (C) 1994-2019 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 1994-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index 5e3d08addd86493b011f0afcdcede6ca857c68b1..fc8ec2f6fcb90cec8dfea0b2f4de364c081a75f2 100644 (file)
@@ -472,6 +472,12 @@ BasicVoiceAudioWaveformStorage                       1.2.840.10008.5.1.4.1.1.9.4
 GeneralAudioWaveformStorage                          1.2.840.10008.5.1.4.1.1.9.4.2
 ArterialPulseWaveformStorage                         1.2.840.10008.5.1.4.1.1.9.5.1
 RespiratoryWaveformStorage                           1.2.840.10008.5.1.4.1.1.9.6.1
+MultichannelRespiratoryWaveformStorage               1.2.840.10008.5.1.4.1.1.9.6.2
+RoutineScalpElectroencephalogramWaveformStorage      1.2.840.10008.5.1.4.1.1.9.7.1
+ElectromyogramWaveformStorage                        1.2.840.10008.5.1.4.1.1.9.7.2
+ElectrooculogramWaveformStorage                      1.2.840.10008.5.1.4.1.1.9.7.3
+SleepElectroencephalogramWaveformStorage             1.2.840.10008.5.1.4.1.1.9.7.4
+BodyPositionWaveformStorage                          1.2.840.10008.5.1.4.1.1.9.8.1
 RETIRED_StandaloneModalityLUTStorage                 1.2.840.10008.5.1.4.1.1.10
 RETIRED_StandaloneVOILUTStorage                      1.2.840.10008.5.1.4.1.1.11
 GrayscaleSoftcopyPresentationStateStorage            1.2.840.10008.5.1.4.1.1.11.1
@@ -526,6 +532,7 @@ WideFieldOphthalmicPhotogr.3DCoordinatesImageStorage 1.2.840.10008.5.1.4.1.1.77.
 OphthalmicOpticalCoherenceTomogr.EnFaceImageStorage  1.2.840.10008.5.1.4.1.1.77.1.5.7
 OphthalmicOpticalCoh.Tomogr.BscanVolumeAnalysisStor. 1.2.840.10008.5.1.4.1.1.77.1.5.8
 VLWholeSlideMicroscopyImageStorage                   1.2.840.10008.5.1.4.1.1.77.1.6
+DermoscopicPhotographyImageStorage                   1.2.840.10008.5.1.4.1.1.77.1.7
 RETIRED_VLMultiframeImageStorage                     1.2.840.10008.5.1.4.1.1.77.2
 LensometryMeasurementsStorage                        1.2.840.10008.5.1.4.1.1.78.1
 AutorefractionMeasurementsStorage                    1.2.840.10008.5.1.4.1.1.78.2
@@ -565,6 +572,8 @@ ContentAssessmentResultsStorage                      1.2.840.10008.5.1.4.1.1.90.
 EncapsulatedPDFStorage                               1.2.840.10008.5.1.4.1.1.104.1
 EncapsulatedCDAStorage                               1.2.840.10008.5.1.4.1.1.104.2
 EncapsulatedSTLStorage                               1.2.840.10008.5.1.4.1.1.104.3
+EncapsulatedOBJStorage                               1.2.840.10008.5.1.4.1.1.104.4
+EncapsulatedMTLStorage                               1.2.840.10008.5.1.4.1.1.104.5
 PositronEmissionTomographyImageStorage               1.2.840.10008.5.1.4.1.1.128
 LegacyConvertedEnhancedPETImageStorage               1.2.840.10008.5.1.4.1.1.128.1
 RETIRED_StandalonePETCurveStorage                    1.2.840.10008.5.1.4.1.1.129
@@ -584,6 +593,13 @@ RTPhysicianIntentStorage                             1.2.840.10008.5.1.4.1.1.481
 RTSegmentAnnotationStorage                           1.2.840.10008.5.1.4.1.1.481.11
 RTRadiationSetStorage                                1.2.840.10008.5.1.4.1.1.481.12
 CArmPhotonElectronRadiationStorage                   1.2.840.10008.5.1.4.1.1.481.13
+TomotherapeuticRadiationStorage                      1.2.840.10008.5.1.4.1.1.481.14
+RoboticArmRadiationStorage                           1.2.840.10008.5.1.4.1.1.481.15
+RTRadiationRecordSetStorage                          1.2.840.10008.5.1.4.1.1.481.16
+RTRadiationSalvageRecordStorage                      1.2.840.10008.5.1.4.1.1.481.17
+TomotherapeuticRadiationRecordStorage                1.2.840.10008.5.1.4.1.1.481.18
+CArmPhotonElectronRadiationRecordStorage             1.2.840.10008.5.1.4.1.1.481.19
+RoboticRadiationRecordStorage                        1.2.840.10008.5.1.4.1.1.481.20
 DICOS_CTImageStorage                                 1.2.840.10008.5.1.4.1.1.501.1
 DICOS_DigitalXRayImageStorageForPresentation         1.2.840.10008.5.1.4.1.1.501.2.1
 DICOS_DigitalXRayImageStorageForProcessing           1.2.840.10008.5.1.4.1.1.501.2.2
@@ -765,6 +781,6 @@ It is an error if no data dictionary can be loaded.
 
 \section movescu_copyright COPYRIGHT
 
-Copyright (C) 1994-2019 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 1994-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index 5ae53a2084a7bde602669442b8ee84dfa6d5a572..13da0b40afa6e4d1d70a5260ee023bce53dd0d41 100644 (file)
@@ -241,10 +241,10 @@ key and certificate file format:
 
 certification authority:
 
-  +cf   --add-cert-file  [c]ertificate filename: string
+  +cf   --add-cert-file  [f]ilename: string
           add certificate file to list of certificates
 
-  +cd   --add-cert-dir  [c]ertificate directory: string
+  +cd   --add-cert-dir  [d]irectory: string
           add certificates in d to list of certificates
 
 security profile:
@@ -381,6 +381,14 @@ data set trailing padding
           align file on multiple of f bytes and items on
           multiple of i bytes
 
+handling of defined length UN elements:
+
+  -uc   --retain-un
+          retain elements as UN (default)
+
+  +uc   --convert-un
+          convert to real VR if known
+
 deflate compression level (only with --write-xfer-deflated/same):
 
   +cl   --compression-level  [l]evel: integer (default: 6)
@@ -628,6 +636,12 @@ BasicVoiceAudioWaveformStorage                       1.2.840.10008.5.1.4.1.1.9.4
 GeneralAudioWaveformStorage                          1.2.840.10008.5.1.4.1.1.9.4.2
 ArterialPulseWaveformStorage                         1.2.840.10008.5.1.4.1.1.9.5.1
 RespiratoryWaveformStorage                           1.2.840.10008.5.1.4.1.1.9.6.1
+MultichannelRespiratoryWaveformStorage               1.2.840.10008.5.1.4.1.1.9.6.2
+RoutineScalpElectroencephalogramWaveformStorage      1.2.840.10008.5.1.4.1.1.9.7.1
+ElectromyogramWaveformStorage                        1.2.840.10008.5.1.4.1.1.9.7.2
+ElectrooculogramWaveformStorage                      1.2.840.10008.5.1.4.1.1.9.7.3
+SleepElectroencephalogramWaveformStorage             1.2.840.10008.5.1.4.1.1.9.7.4
+BodyPositionWaveformStorage                          1.2.840.10008.5.1.4.1.1.9.8.1
 RETIRED_StandaloneModalityLUTStorage                 1.2.840.10008.5.1.4.1.1.10
 RETIRED_StandaloneVOILUTStorage                      1.2.840.10008.5.1.4.1.1.11
 GrayscaleSoftcopyPresentationStateStorage            1.2.840.10008.5.1.4.1.1.11.1
@@ -682,6 +696,7 @@ WideFieldOphthalmicPhotogr.3DCoordinatesImageStorage 1.2.840.10008.5.1.4.1.1.77.
 OphthalmicOpticalCoherenceTomogr.EnFaceImageStorage  1.2.840.10008.5.1.4.1.1.77.1.5.7
 OphthalmicOpticalCoh.Tomogr.BscanVolumeAnalysisStor. 1.2.840.10008.5.1.4.1.1.77.1.5.8
 VLWholeSlideMicroscopyImageStorage                   1.2.840.10008.5.1.4.1.1.77.1.6
+DermoscopicPhotographyImageStorage                   1.2.840.10008.5.1.4.1.1.77.1.7
 RETIRED_VLMultiframeImageStorage                     1.2.840.10008.5.1.4.1.1.77.2
 LensometryMeasurementsStorage                        1.2.840.10008.5.1.4.1.1.78.1
 AutorefractionMeasurementsStorage                    1.2.840.10008.5.1.4.1.1.78.2
@@ -721,6 +736,8 @@ ContentAssessmentResultsStorage                      1.2.840.10008.5.1.4.1.1.90.
 EncapsulatedPDFStorage                               1.2.840.10008.5.1.4.1.1.104.1
 EncapsulatedCDAStorage                               1.2.840.10008.5.1.4.1.1.104.2
 EncapsulatedSTLStorage                               1.2.840.10008.5.1.4.1.1.104.3
+EncapsulatedOBJStorage                               1.2.840.10008.5.1.4.1.1.104.4
+EncapsulatedMTLStorage                               1.2.840.10008.5.1.4.1.1.104.5
 PositronEmissionTomographyImageStorage               1.2.840.10008.5.1.4.1.1.128
 LegacyConvertedEnhancedPETImageStorage               1.2.840.10008.5.1.4.1.1.128.1
 RETIRED_StandalonePETCurveStorage                    1.2.840.10008.5.1.4.1.1.129
@@ -740,6 +757,13 @@ RTPhysicianIntentStorage                             1.2.840.10008.5.1.4.1.1.481
 RTSegmentAnnotationStorage                           1.2.840.10008.5.1.4.1.1.481.11
 RTRadiationSetStorage                                1.2.840.10008.5.1.4.1.1.481.12
 CArmPhotonElectronRadiationStorage                   1.2.840.10008.5.1.4.1.1.481.13
+TomotherapeuticRadiationStorage                      1.2.840.10008.5.1.4.1.1.481.14
+RoboticArmRadiationStorage                           1.2.840.10008.5.1.4.1.1.481.15
+RTRadiationRecordSetStorage                          1.2.840.10008.5.1.4.1.1.481.16
+RTRadiationSalvageRecordStorage                      1.2.840.10008.5.1.4.1.1.481.17
+TomotherapeuticRadiationRecordStorage                1.2.840.10008.5.1.4.1.1.481.18
+CArmPhotonElectronRadiationRecordStorage             1.2.840.10008.5.1.4.1.1.481.19
+RoboticRadiationRecordStorage                        1.2.840.10008.5.1.4.1.1.481.20
 DICOS_CTImageStorage                                 1.2.840.10008.5.1.4.1.1.501.1
 DICOS_DigitalXRayImageStorageForPresentation         1.2.840.10008.5.1.4.1.1.501.2.1
 DICOS_DigitalXRayImageStorageForProcessing           1.2.840.10008.5.1.4.1.1.501.2.2
@@ -912,6 +936,6 @@ It is an error if no data dictionary can be loaded.
 
 \section storescp_copyright COPYRIGHT
 
-Copyright (C) 1996-2019 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 1996-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index d4a25cf0f74adb9fc1126754f1741d953bb765fd..74746e6725ec058a0bb576507f35068543e3cd63 100644 (file)
@@ -323,10 +323,10 @@ key and certificate file format:
 
 certification authority:
 
-  +cf   --add-cert-file  [c]ertificate filename: string
+  +cf   --add-cert-file  [f]ilename: string
           add certificate file to list of certificates
 
-  +cd   --add-cert-dir  [c]ertificate directory: string
+  +cd   --add-cert-dir  [d]irectory: string
           add certificates in d to list of certificates
 
 security profile:
@@ -580,6 +580,6 @@ It is an error if no data dictionary can be loaded.
 
 \section storescu_copyright COPYRIGHT
 
-Copyright (C) 1996-2019 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 1996-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index 6d83ff4e5b0a230a0584bceafcd5e0793ab27d6e..2fba26e7387792de2d5e3919335e9c704c37aabb 100644 (file)
@@ -1,5 +1,5 @@
 #
-#  Copyright (C) 2003-2019, OFFIS e.V.
+#  Copyright (C) 2003-2020, OFFIS e.V.
 #  All rights reserved.  See COPYRIGHT file for details.
 #
 #  This software and supporting documentation were developed by
@@ -205,14 +205,21 @@ PresentationContext128 = DRAFT_WaveformStorage\UncompressedOrZlib
 #
 # - AcquisitionContextSRStorage
 # - AdvancedBlendingPresentationStateStorage
+# - BodyPositionWaveformStorage
 # - BreastProjectionXRayImageStorageForPresentation
 # - BreastProjectionXRayImageStorageForProcessing
+# - CArmPhotonElectronRadiationRecordStorage
 # - CArmPhotonElectronRadiationStorage
 # - ColorPaletteStorage
 # - CompositingPlanarMPRVolumetricPresentationStateStorage
 # - ContentAssessmentResultsStorage
 # - CTDefinedProcedureProtocolStorage
 # - CTPerformedProcedureProtocolStorage
+# - DermoscopicPhotographyImageStorage
+# - ElectromyogramWaveformStorage
+# - ElectrooculogramWaveformStorage
+# - EncapsulatedMTLStorage
+# - EncapsulatedOBJStorage
 # - EncapsulatedSTLStorage
 # - ExtensibleSRStorage
 # - GrayscalePlanarMPRVolumetricPresentationStateStorage
@@ -220,6 +227,7 @@ PresentationContext128 = DRAFT_WaveformStorage\UncompressedOrZlib
 # - LegacyConvertedEnhancedCTImageStorage
 # - LegacyConvertedEnhancedMRImageStorage
 # - LegacyConvertedEnhancedPETImageStorage
+# - MultichannelRespiratoryWaveformStorage
 # - MultipleVolumeRenderingVolumetricPresentationStateStorage
 # - OphthalmicOpticalCoherenceTomographyBscanVolumeAnalysisStorage
 # - OphthalmicOpticalCoherenceTomographyEnFaceImageStorage
@@ -229,12 +237,20 @@ PresentationContext128 = DRAFT_WaveformStorage\UncompressedOrZlib
 # - PlannedImagingAgentAdministrationSRStorage
 # - ProtocolApprovalStorage
 # - RadiopharmaceuticalRadiationDoseSRStorage
+# - RoboticArmRadiationStorage
+# - RoboticRadiationRecordStorage
+# - RoutineScalpElectroencephalogramWaveformStorage
 # - RTBrachyApplicationSetupDeliveryInstructionStorage
 # - RTPhysicianIntentStorage
+# - RTRadiationRecordSetStorage
+# - RTRadiationSalvageRecordStorage
 # - RTRadiationSetStorage
 # - RTSegmentAnnotationStorage
 # - SegmentedVolumeRenderingVolumetricPresentationStateStorage
 # - SimplifiedAdultEchoSRStorage
+# - SleepElectroencephalogramWaveformStorage
+# - TomotherapeuticRadiationRecordStorage
+# - TomotherapeuticRadiationStorage
 # - TractographyResultsStorage
 # - VolumeRenderingVolumetricPresentationStateStorage
 # - WideFieldOphthalmicPhotographyStereographicProjectionImageStorage
@@ -398,9 +414,17 @@ PresentationContext128 = XRayRadiationDoseSRStorage\UncompressedOrZlib
 # the following SOP classes are missing in the above list:
 #
 # - AdvancedBlendingPresentationStateStorage
+# - BodyPositionWaveformStorage
+# - CArmPhotonElectronRadiationRecordStorage
 # - CArmPhotonElectronRadiationStorage
 # - ColorPaletteStorage
+# - DermoscopicPhotographyImageStorage
+# - ElectromyogramWaveformStorage
+# - ElectrooculogramWaveformStorage
+# - EncapsulatedMTLStorage
+# - EncapsulatedOBJStorage
 # - EncapsulatedSTLStorage
+# - MultichannelRespiratoryWaveformStorage
 # - MultipleVolumeRenderingVolumetricPresentationStateStorage
 # - OphthalmicOpticalCoherenceTomographyBscanVolumeAnalysisStorage
 # - OphthalmicOpticalCoherenceTomographyEnFaceImageStorage
@@ -408,10 +432,18 @@ PresentationContext128 = XRayRadiationDoseSRStorage\UncompressedOrZlib
 # - PerformedImagingAgentAdministrationSRStorage
 # - PlannedImagingAgentAdministrationSRStorage
 # - ProtocolApprovalStorage
+# - RoboticArmRadiationStorage
+# - RoboticRadiationRecordStorage
+# - RoutineScalpElectroencephalogramWaveformStorage
 # - RTPhysicianIntentStorage
+# - RTRadiationRecordSetStorage
+# - RTRadiationSalvageRecordStorage
 # - RTRadiationSetStorage
 # - RTSegmentAnnotationStorage
 # - SegmentedVolumeRenderingVolumetricPresentationStateStorage
+# - SleepElectroencephalogramWaveformStorage
+# - TomotherapeuticRadiationRecordStorage
+# - TomotherapeuticRadiationStorage
 # - VolumeRenderingVolumetricPresentationStateStorage
 #
 # - RETIRED_HardcopyColorImageStorage
index 252ff183696bf9ebad20b6ebfc92c2006064d5a3..e915a09ed5260707125ad2ae092ea44467d36038 100644 (file)
@@ -1,5 +1,5 @@
 #
-#  Copyright (C) 2003-2019, OFFIS e.V.
+#  Copyright (C) 2003-2020, OFFIS e.V.
 #  All rights reserved.  See COPYRIGHT file for details.
 #
 #  This software and supporting documentation were developed by
@@ -205,9 +205,11 @@ PresentationContext128 = VideoPhotographicImageStorage\MPEG2
 # - AutorefractionMeasurementsStorage
 # - BasicStructuredDisplayStorage
 # - BlendingSoftcopyPresentationStateStorage
+# - BodyPositionWaveformStorage
 # - BreastProjectionXRayImageStorageForPresentation
 # - BreastProjectionXRayImageStorageForProcessing
 # - BreastTomosynthesisImageStorage
+# - CArmPhotonElectronRadiationRecordStorage
 # - CArmPhotonElectronRadiationStorage
 # - CompositingPlanarMPRVolumetricPresentationStateStorage
 # - Comprehensive3DSRStorage
@@ -216,7 +218,12 @@ PresentationContext128 = VideoPhotographicImageStorage\MPEG2
 # - CTDefinedProcedureProtocolStorage
 # - CTPerformedProcedureProtocolStorage
 # - DeformableSpatialRegistrationStorage
+# - DermoscopicPhotographyImageStorage
+# - ElectromyogramWaveformStorage
+# - ElectrooculogramWaveformStorage
 # - EncapsulatedCDAStorage
+# - EncapsulatedMTLStorage
+# - EncapsulatedOBJStorage
 # - EncapsulatedSTLStorage
 # - EnhancedMRColorImageStorage
 # - EnhancedPETImageStorage
@@ -237,6 +244,7 @@ PresentationContext128 = VideoPhotographicImageStorage\MPEG2
 # - LegacyConvertedEnhancedPETImageStorage
 # - LensometryMeasurementsStorage
 # - MacularGridThicknessAndVolumeReportStorage
+# - MultichannelRespiratoryWaveformStorage
 # - MultipleVolumeRenderingVolumetricPresentationStateStorage
 # - OphthalmicAxialMeasurementsStorage
 # - OphthalmicOpticalCoherenceTomographyBscanVolumeAnalysisStorage
@@ -252,21 +260,29 @@ PresentationContext128 = VideoPhotographicImageStorage\MPEG2
 # - RadiopharmaceuticalRadiationDoseSRStorage
 # - RealWorldValueMappingStorage
 # - RespiratoryWaveformStorage
+# - RoboticArmRadiationStorage
+# - RoboticRadiationRecordStorage
+# - RoutineScalpElectroencephalogramWaveformStorage
 # - RTBeamsDeliveryInstructionStorage
 # - RTBrachyApplicationSetupDeliveryInstructionStorage
 # - RTIonBeamsTreatmentRecordStorage
 # - RTIonPlanStorage
 # - RTPhysicianIntentStorage
+# - RTRadiationRecordSetStorage
+# - RTRadiationSalvageRecordStorage
 # - RTRadiationSetStorage
 # - RTSegmentAnnotationStorage
 # - SegmentationStorage
 # - SegmentedVolumeRenderingVolumetricPresentationStateStorage
 # - SimplifiedAdultEchoSRStorage
+# - SleepElectroencephalogramWaveformStorage
 # - SpectaclePrescriptionReportStorage
 # - SubjectiveRefractionMeasurementsStorage
 # - SurfaceScanMeshStorage
 # - SurfaceScanPointCloudStorage
 # - SurfaceSegmentationStorage
+# - TomotherapeuticRadiationRecordStorage
+# - TomotherapeuticRadiationStorage
 # - TractographyResultsStorage
 # - VisualAcuityMeasurementsStorage
 # - VLWholeSlideMicroscopyImageStorage
index 088aa072ad938552a881688836e71ab89be713f8..76231def189d602591472e3d527cfbafb7659863 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2018, OFFIS e.V.
+ *  Copyright (C) 1994-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -147,12 +147,14 @@ public:
    *    If NULL, the current directory is used.
    *  @param outputStream pointer to output stream that is used when extractResponses is set
    *    to FEM_singleXMLFile.
+   *  @param limitOutput maximum number of responses written to file (0 means unlimited)
    */
   DcmFindSCUDefaultCallback(
     DcmFindSCUExtractMode extractResponses,
     int cancelAfterNResponses,
     const char *outputDirectory = NULL,
-    STD_NAMESPACE ofstream *outputStream = NULL);
+    STD_NAMESPACE ofstream *outputStream = NULL,
+    const unsigned int limitOutput = 0);
 
   /// destructor
   virtual ~DcmFindSCUDefaultCallback() {}
@@ -172,10 +174,13 @@ public:
 private:
 
    /// mode specifying whether and how to extract C-FIND responses.
-   DcmFindSCUExtractMode extractResponses_;
+   const DcmFindSCUExtractMode extractResponses_;
 
    /// if non-negative, a C-FIND-CANCEL will be issued after the given number of incoming C-FIND-RSP messages.
-   int cancelAfterNResponses_;
+   const int cancelAfterNResponses_;
+
+   /// maximum number of responses written to file (default: unlimited)
+   const unsigned int limitOutput_;
 
    /// directory used to store the output files (e.g. response datasets).
    OFString outputDirectory_;
@@ -200,6 +205,15 @@ public:
   /// destructor. Destroys network structure if not done already.
   virtual ~DcmFindSCU();
 
+  /** set maximum number of responses written to file.
+   *  Limiting the number of responses written to file might be useful e.g. if the
+   *  C-FIND-CANCEL request does not prevent the SCP from sending further C-FIND-RSP
+   *  messages.  Also see various "extract" parameters of performQuery() method.
+   *  @param limit maximum number of responses written to file (0 means unlimited)
+   *  @return EC_Normal if successful, an error code otherwise.
+   */
+  OFCondition setOutputResponseLimit(const unsigned int limit);
+
   /** initialize the network structure. This should be done only once.
    *  @param acse_timeout timeout for ACSE operations, in seconds
    *  @return EC_Normal if successful, an error code otherwise.
@@ -376,6 +390,9 @@ private:
   /// pointer to network structure
   T_ASC_Network *net_;
 
+  /// maximum number of responses written to file (default: unlimited)
+  unsigned int outputResponseLimit_;
+
 };
 
 #endif
index e03a63dc061be11b4380ede6154d12dfe1b2ce11..e9da634abe7fd6275dd3b97a26124eba4684e0e7 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were partly developed by
@@ -124,53 +124,119 @@ extern DCMTK_DCMNET_EXPORT OFGlobal<Uint32> dcmMaxOutgoingPDUSize; /* default 2^
  * General Status Codes.
  */
 #define STATUS_Success  0x0000
-#define STATUS_Pending  0xff00
+#define STATUS_Pending  0xff00  // deprecated, will be removed in a future version
 
-#define DICOM_PENDING_STATUS(status)  (((status) & 0xff00) == 0xff00)
-#define DICOM_WARNING_STATUS(status) ((((status) & 0xf000) == 0xb000) || ((status) == 0x0107) || ((status) == 0x0116))
+/*
+ * Status Classes (see DICOM PS3.7 Annex C).
+ */
+#define DICOM_SUCCESS_STATUS(status)  ((status) == 0x0000)
+#define DICOM_FAILURE_STATUS(status)  ((((status) & 0xf000) == 0xa000) || (((status) & 0xf000) == 0xc000) || ((((status) & 0xff00) == 0x0100) && ((status) != 0x0107) && ((status) != 0x0116)) || (((status) & 0xff00) == 0x0200))
+#define DICOM_WARNING_STATUS(status)  ((((status) & 0xf000) == 0xb000) || ((status) == 0x0001) || ((status) == 0x0107) || ((status) == 0x0116))
+#define DICOM_CANCEL_STATUS(status)   ((status) == 0xfe00)
+#define DICOM_PENDING_STATUS(status)  (((status) == 0xff00) || ((status) == 0xff01))
+#define DICOM_STANDARD_STATUS(status) (((status) == 0x0000) || ((status) == 0x0001) || (((status) & 0xff00) == 0x0100) || (((status) & 0xff00) == 0x0200) || (((status) & 0xf000) == 0xa000) || (((status) & 0xf000) == 0xb000) || (((status) & 0xf000) == 0xc000) || ((status) == 0xfe00) || ((status) == 0xff00) || ((status) == 0xff01))
 
 /*
  * Service Class Specific Status Codes.
- * NOTE: some codes are only significant in the high byte
- * or high nibble (4 bits).
+ * NOTE: some codes are only significant in the high byte or high nibble (4 bits).
  */
-/* Storage Specific Codes*/
-#define STATUS_STORE_Refused_OutOfResources             /* high byte */ 0xa700
+
+/* General C-ECHO Codes */
+#define STATUS_ECHO_Success                                             0x0000
+#define STATUS_ECHO_Refused_SOPClassNotSupported                        0x0122
+#define STATUS_ECHO_DuplicateInvocation                                 0x0210
+#define STATUS_ECHO_UnrecognizedOperation                               0x0211
+#define STATUS_ECHO_MistypedArgument                                    0x0212
+
+/* General C-STORE Codes */
+#define STATUS_STORE_Success                                            0x0000
 #define STATUS_STORE_Refused_SOPClassNotSupported                       0x0122
+#define STATUS_STORE_Refused_NotAuthorized                              0x0124
+#define STATUS_STORE_InvalidSOPClass                                    0x0117
+#define STATUS_STORE_DuplicateInvocation                                0x0210
+#define STATUS_STORE_UnrecognizedOperation                              0x0211
+#define STATUS_STORE_MistypedArgument                                   0x0212
+/* Service Class Specific C-STORE Codes (Storage) */
+#define STATUS_STORE_Refused_OutOfResources             /* high byte */ 0xa700
 #define STATUS_STORE_Error_DataSetDoesNotMatchSOPClass  /* high byte */ 0xa900
 #define STATUS_STORE_Error_CannotUnderstand           /* high nibble */ 0xc000
 #define STATUS_STORE_Warning_CoercionOfDataElements                     0xb000
 #define STATUS_STORE_Warning_DataSetDoesNotMatchSOPClass                0xb007
 #define STATUS_STORE_Warning_ElementsDiscarded                          0xb006
 
-/* Find Specific Codes */
-#define STATUS_FIND_Refused_OutOfResources                              0xa700
+/* General C-FIND Codes */
+#define STATUS_FIND_Success                                             0x0000
 #define STATUS_FIND_Refused_SOPClassNotSupported                        0x0122
-#define STATUS_FIND_Failed_IdentifierDoesNotMatchSOPClass               0xa900
+#define STATUS_FIND_Cancel                                              0xfe00
+/* Service Class Specific C-FIND Codes */
+/* (Query/Retrieve, Modality Worklist Management, Relevant Patient Information Query) */
+#define STATUS_FIND_Success_MatchingIsComplete                          0x0000
+#define STATUS_FIND_Refused_OutOfResources                              0xa700
+#define STATUS_FIND_Failed_IdentifierDoesNotMatchSOPClass               0xa900  // deprecated, will be removed in a future version
+#define STATUS_FIND_Error_DataSetDoesNotMatchSOPClass                   0xa900
 #define STATUS_FIND_Failed_UnableToProcess            /* high nibble */ 0xc000
+#define STATUS_FIND_Failed_MoreThanOneMatchFound                        0xc100
+#define STATUS_FIND_Failed_UnableToSupportRequestedTemplate             0xc200
 #define STATUS_FIND_Cancel_MatchingTerminatedDueToCancelRequest         0xfe00
+#define STATUS_FIND_Pending_MatchesAreContinuing                        0xff00
 #define STATUS_FIND_Pending_WarningUnsupportedOptionalKeys              0xff01
 
-/* Move Specific Codes */
+/* General C-MOVE Codes */
+#define STATUS_MOVE_Success                                             0x0000
+#define STATUS_MOVE_Refused_SOPClassNotSupported                        0x0122
+#define STATUS_MOVE_Refused_NotAuthorized                               0x0124
+#define STATUS_MOVE_Cancel                                              0xfe00
+#define STATUS_MOVE_DuplicateInvocation                                 0x0210
+#define STATUS_MOVE_UnrecognizedOperation                               0x0211
+#define STATUS_MOVE_MistypedArgument                                    0x0212
+/* Service Class Specific C-MOVE Codes */
+/* (Query/Retrieve, Composite Instance Root Retrieve) */
+#define STATUS_MOVE_Success_SubOperationsCompleteNoFailures             0x0000
 #define STATUS_MOVE_Refused_OutOfResourcesNumberOfMatches               0xa701
 #define STATUS_MOVE_Refused_OutOfResourcesSubOperations                 0xa702
-#define STATUS_MOVE_Failed_SOPClassNotSupported                         0x0122
-#define STATUS_MOVE_Failed_MoveDestinationUnknown                       0xa801
-#define STATUS_MOVE_Failed_IdentifierDoesNotMatchSOPClass               0xa900
+#define STATUS_MOVE_Refused_MoveDestinationUnknown                      0xa801
+#define STATUS_MOVE_Failed_SOPClassNotSupported                         0x0122  // deprecated, will be removed in a future version
+#define STATUS_MOVE_Failed_MoveDestinationUnknown                       0xa801  // deprecated, will be removed in a future version
+#define STATUS_MOVE_Failed_IdentifierDoesNotMatchSOPClass               0xa900  // deprecated, will be removed in a future version
+#define STATUS_MOVE_Error_DataSetDoesNotMatchSOPClass                   0xa900
+#define STATUS_MOVE_Failed_NoneOfTheFramesWereFoundInSOPInstance        0xaa00
+#define STATUS_MOVE_Failed_UnableToCreateNewObjectForThisSOPClass       0xaa01
+#define STATUS_MOVE_Failed_UnableToExtractFrames                        0xaa02
+#define STATUS_MOVE_Failed_TimeBasedRequestForNonTimeBasedSOPInstance   0xaa03
+#define STATUS_MOVE_Failed_InvalidRequest                               0xaa04
 #define STATUS_MOVE_Failed_UnableToProcess            /* high nibble */ 0xc000
 #define STATUS_MOVE_Cancel_SubOperationsTerminatedDueToCancelIndication 0xfe00
 #define STATUS_MOVE_Warning_SubOperationsCompleteOneOrMoreFailures      0xb000
-
-/* Get Specific Codes */
+#define STATUS_MOVE_Pending_SubOperationsAreContinuing                  0xff00
+
+/* General C-GET Codes */
+#define STATUS_GET_Success                                              0x0000
+#define STATUS_GET_Refused_SOPClassNotSupported                         0x0122
+#define STATUS_GET_Cancel                                               0xfe00
+#define STATUS_GET_DuplicateInvocation                                  0x0210
+#define STATUS_GET_UnrecognizedOperation                                0x0211
+#define STATUS_GET_MistypedArgument                                     0x0212
+/* Service Class Specific C-GET Codes */
+/* (Query/Retrieve, Composite Instance Root Retrieve and others) */
+#define STATUS_GET_Success_SubOperationsCompleteNoFailures              0x0000
 #define STATUS_GET_Refused_OutOfResourcesNumberOfMatches                0xa701
 #define STATUS_GET_Refused_OutOfResourcesSubOperations                  0xa702
-#define STATUS_GET_Failed_SOPClassNotSupported                          0x0122
-#define STATUS_GET_Failed_IdentifierDoesNotMatchSOPClass                0xa900
+#define STATUS_GET_Failed_SOPClassNotSupported                          0x0122  // deprecated, will be removed in a future version
+#define STATUS_GET_Failed_IdentifierDoesNotMatchSOPClass                0xa900  // deprecated, will be removed in a future version
+#define STATUS_GET_Error_DataSetDoesNotMatchSOPClass                    0xa900
+#define STATUS_GET_Failed_NoneOfTheFramesWereFoundInSOPInstance         0xaa00
+#define STATUS_GET_Failed_UnableToCreateNewObjectForThisSOPClass        0xaa01
+#define STATUS_GET_Failed_UnableToExtractFrames                         0xaa02
+#define STATUS_GET_Failed_TimeBasedRequestForNonTimeBasedSOPInstance    0xaa03
+#define STATUS_GET_Failed_InvalidRequest                                0xaa04
 #define STATUS_GET_Failed_UnableToProcess             /* high nibble */ 0xc000
 #define STATUS_GET_Cancel_SubOperationsTerminatedDueToCancelIndication  0xfe00
 #define STATUS_GET_Warning_SubOperationsCompleteOneOrMoreFailures       0xb000
+#define STATUS_GET_Pending_SubOperationsAreContinuing                   0xff00
 
-/* DIMSE-N Specific Codes */
+/* General DIMSE-N Codes */
+#define STATUS_N_Success                                                0x0000
+#define STATUS_N_Refused_NotAuthorized                                  0x0124
 #define STATUS_N_Cancel                                                 0xfe00
 #define STATUS_N_AttributeListError                                     0x0107
 #define STATUS_N_SOPClassNotSupported                                   0x0122
@@ -180,32 +246,66 @@ extern DCMTK_DCMNET_EXPORT OFGlobal<Uint32> dcmMaxOutgoingPDUSize; /* default 2^
 #define STATUS_N_InvalidArgumentValue                                   0x0115
 #define STATUS_N_InvalidAttributeValue                                  0x0106
 #define STATUS_N_AttributeValueOutOfRange                               0x0116
-#define STATUS_N_InvalidObjectInstance                                  0x0117
+#define STATUS_N_InvalidObjectInstance                                  0x0117  // deprecated, will be removed in a future version
+#define STATUS_N_InvalidSOPInstance                                     0x0117
 #define STATUS_N_MissingAttribute                                       0x0120
 #define STATUS_N_MissingAttributeValue                                  0x0121
 #define STATUS_N_MistypedArgument                                       0x0212
+#define STATUS_N_NoSuchAction                                           0x0123
 #define STATUS_N_NoSuchArgument                                         0x0114
 #define STATUS_N_NoSuchAttribute                                        0x0105
 #define STATUS_N_NoSuchEventType                                        0x0113
-#define STATUS_N_NoSuchObjectInstance                                   0x0112
+#define STATUS_N_NoSuchObjectInstance                                   0x0112  // deprecated, will be removed in a future version
+#define STATUS_N_NoSuchSOPInstance                                      0x0112
 #define STATUS_N_NoSuchSOPClass                                         0x0118
 #define STATUS_N_ProcessingFailure                                      0x0110
 #define STATUS_N_ResourceLimitation                                     0x0213
 #define STATUS_N_UnrecognizedOperation                                  0x0211
-#define STATUS_N_NoSuchAction                                           0x0123
+/* the following Codes are used by multiple Services */
+#define STATUS_N_Warning_RequestedOptionalAttributesNotSupported        0x0001
 
-/* Print Management Service Class Specific Codes */
+/* Service Class Specific DIMSE-N Codes */
+/* (Print Management) */
 #define STATUS_N_PRINT_BFS_Warn_MemoryAllocation                        0xb600
 #define STATUS_N_PRINT_BFS_Warn_NoSessionPrinting                       0xb601
 #define STATUS_N_PRINT_BFS_Warn_EmptyPage                               0xb602
 #define STATUS_N_PRINT_BFB_Warn_EmptyPage                               0xb603
+#define STATUS_N_PRINT_BFS_BFB_IB_Warn_ImageDemagnified                 0xb604
+#define STATUS_N_PRINT_BFS_BFB_IB_Warn_ImageCropped                     0xb609
+#define STATUS_N_PRINT_BFS_BFB_IB_Warn_ImageDecimated                   0xb60a
 #define STATUS_N_PRINT_BFS_Fail_NoFilmBox                               0xc600
 #define STATUS_N_PRINT_BFS_Fail_PrintQueueFull                          0xc601
-#define STATUS_N_PRINT_BSB_Fail_PrintQueueFull                          0xc602
+#define STATUS_N_PRINT_BFB_Fail_PrintQueueFull                          0xc602
 #define STATUS_N_PRINT_BFS_BFB_Fail_ImageSize                           0xc603
-#define STATUS_N_PRINT_BFS_BFB_Fail_PositionCollision                   0xc604
+#define STATUS_N_PRINT_BFS_BFB_Fail_PositionCollision                   0xc604  // retired, see DICOM PS3.4
+#define STATUS_N_PRINT_BFS_BFB_Fail_CombinedImageSize                   0xc613
+#define STATUS_N_PRINT_IB_Warn_MinMaxDensity                            0xb605
 #define STATUS_N_PRINT_IB_Fail_InsufficientMemory                       0xc605
 #define STATUS_N_PRINT_IB_Fail_MoreThanOneVOILUT                        0xc606
+/* (Modality Performed Procedure Step Retrieve) */
+#define STATUS_N_MPPS_Warning_RequestedOptionalAttributesNotSupported   0x0001
+/* (Application Event Logging) */
+#define STATUS_N_LOG_Failure_ProceduralLoggingNotAvailable              0xc101
+#define STATUS_N_LOG_Failure_EventInformationDoesNotMatchTemplate       0xc102
+#define STATUS_N_LOG_Failure_CannotMatchEventToCurrentStudy             0xc103
+#define STATUS_N_LOG_Failure_IDsInconsistentInMatchingCurrentStudy      0xc104
+#define STATUS_N_LOG_Warning_SynchronizationFrameOfReferenceDoesNotMatch 0xb101
+#define STATUS_N_LOG_Warning_StudyInstanceUIDCoercion                   0xb102
+#define STATUS_N_LOG_Warning_IDsInconsistentInMatchingCurrentStudy      0xb104
+/* (Media Creation Management) */
+#define STATUS_N_MEDIA_Failed_MediaCreationActionAlreadyReceived        0xa510
+#define STATUS_N_MEDIA_Failed_MediaCreationRequestAlreadyCompleted      0xc201
+#define STATUS_N_MEDIA_Failed_MediaCreationRequestAlreadyInProgress     0xc202
+#define STATUS_N_MEDIA_Failed_CancellationDenied                        0xc203
+#define STATUS_N_MEDIA_Warning_RequestedOptionalAttributesNotSupported  0x0001
+
+// --- TODO (DIMSE-N) ---
+
+// the following Services use different DIMSE Status Code meanings for
+// each SOP Class, including standard Codes such as 0x0000 (Success):
+
+/* (Unified Procedure Step) */
+/* (RT Machine Verification) */
 
 
 /*
index dd1eb355ad9050de9d630bfb201fff7893831d3f..5191f670d48bc75d56a392ecd1477c1326e14cda 100644 (file)
@@ -139,7 +139,7 @@ DCMTK_DCMNET_EXPORT const char *DU_neventReportStatusString(Uint16 statusCode);
 /** Logs result of a select() call. According to the select() documentation,
  *  a value of > 1 means that data has arrived. This is logged on TRACE level
  *  since it should be a very regular case. If select() returns 0, a timeout
- *  has occured, and in case of -1 another error happened (e.g. interrupt).
+ *  has occurred, and in case of -1 another error happened (e.g. interrupt).
  *  These two events are logged to DEBUG log level.
  *  Note that this function makes use of errno (Unix) or WSAGetLastError()
  *  (Windows aka Winsock), so it must be called right after the select() call
index 9e87d22d0f29b59c0803c5e2adfeecd1c67f39f5..aa808e768f076a60726ce814d9c1d440f944d5d8 100644 (file)
@@ -402,7 +402,7 @@ typedef enum {
 */
 
 #define DUL_DULCOMPAT     2768240730UL
-#define DUL_DIMSECOMPAT   983040UL
+#define DUL_DIMSECOMPAT   1048576UL
 #define DUL_MAXPDUCOMPAT  4278190335UL
 
 /* Define the function prototypes for this facility.
index de7ec18744eaff5c4febb83e4d62b9017e2de92e..17c54c1dfbccc8d272be481458c7fc69fc54ff42 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2009-2018, OFFIS e.V.
+ *  Copyright (C) 2009-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #ifndef SCP_H
 #define SCP_H
 
-#include "dcmtk/config/osconfig.h"  /* make sure OS specific configuration is included first */
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 
-#include "dcmtk/oflog/oflog.h"
-#include "dcmtk/dcmdata/dctk.h"     /* Covers most common dcmdata classes */
+#include "dcmtk/dcmdata/dctk.h" /* Covers most common dcmdata classes */
 #include "dcmtk/dcmnet/assoc.h"
-#include "dcmtk/dcmnet/dimse.h"     /* DIMSE network layer */
+#include "dcmtk/dcmnet/dimse.h"  /* DIMSE network layer */
+#include "dcmtk/dcmnet/diutil.h" /* for DCMNET_WARN() */
 #include "dcmtk/dcmnet/scpcfg.h"
-#include "dcmtk/dcmnet/diutil.h"    /* for DCMNET_WARN() */
-
+#include "dcmtk/oflog/oflog.h"
 
 // include this file in doxygen documentation
 
  *  @brief general Service Class Provider (SCP) class
  */
 
-
 /** Structure representing single process in multi-process mode
  */
 struct DCMTK_DCMNET_EXPORT DcmProcessSlotType
 {
-  /// Name of peer
-  DIC_NODENAME peerName;
-  /// Calling AE title
-  DIC_AE callingAETitle;
-  /// Called AE title
-  DIC_AE calledAETitle;
-  /// Process ID
-  int processId;
-  /// Start time
-  time_t startTime;
-  /// Indicator if process has storage ability
-  OFBool hasStorageAbility;
+    /// Name of peer
+    DIC_NODENAME peerName;
+    /// Calling AE title
+    DIC_AE callingAETitle;
+    /// Called AE title
+    DIC_AE calledAETitle;
+    /// Process ID
+    int processId;
+    /// Start time
+    time_t startTime;
+    /// Indicator if process has storage ability
+    OFBool hasStorageAbility;
 };
 
 /** Action codes that can be given to DcmSCP to control behavior during SCP's operation.
@@ -63,36 +61,36 @@ struct DCMTK_DCMNET_EXPORT DcmProcessSlotType
  */
 enum DcmSCPActionType
 {
-  /// No action defined
-  DCMSCP_ACTION_UNDEFINED,
-  /// Tell SCP to refuse association
-  DCMSCP_ACTION_REFUSE_ASSOCIATION
+    /// No action defined
+    DCMSCP_ACTION_UNDEFINED,
+    /// Tell SCP to refuse association
+    DCMSCP_ACTION_REFUSE_ASSOCIATION
 };
 
 /** Codes denoting a reason for refusing an association
  */
 enum DcmRefuseReasonType
 {
-  /// Too many associations (SCP cannot handle a further association)
-  DCMSCP_TOO_MANY_ASSOCIATIONS,
-  /// Forking a new SCP process failed
-  DCMSCP_CANNOT_FORK,
-  /// Refusing association because of bad application context name
-  DCMSCP_BAD_APPLICATION_CONTEXT_NAME,
-  /// Refusing association because of disallowed connecting host
-  DCMSCP_CALLING_HOST_NOT_ALLOWED,
-  /// Refusing association because of unaccepted called AE title
-  DCMSCP_CALLED_AE_TITLE_NOT_RECOGNIZED,
-  /// Refusing association because of unaccepted calling AE title
-  DCMSCP_CALLING_AE_TITLE_NOT_RECOGNIZED,
-  /// Refusing association because SCP was forced to do so
-  DCMSCP_FORCED,
-  /// Refusing association because of missing Implementation Class UID
-  DCMSCP_NO_IMPLEMENTATION_CLASS_UID,
-  /// Refusing association because of no acceptable Presentation Contexts
-  DCMSCP_NO_PRESENTATION_CONTEXTS,
-  /// Refusing association because of internal error
-  DCMSCP_INTERNAL_ERROR
+    /// Too many associations (SCP cannot handle a further association)
+    DCMSCP_TOO_MANY_ASSOCIATIONS,
+    /// Forking a new SCP process failed
+    DCMSCP_CANNOT_FORK,
+    /// Refusing association because of bad application context name
+    DCMSCP_BAD_APPLICATION_CONTEXT_NAME,
+    /// Refusing association because of disallowed connecting host
+    DCMSCP_CALLING_HOST_NOT_ALLOWED,
+    /// Refusing association because of unaccepted called AE title
+    DCMSCP_CALLED_AE_TITLE_NOT_RECOGNIZED,
+    /// Refusing association because of unaccepted calling AE title
+    DCMSCP_CALLING_AE_TITLE_NOT_RECOGNIZED,
+    /// Refusing association because SCP was forced to do so
+    DCMSCP_FORCED,
+    /// Refusing association because of missing Implementation Class UID
+    DCMSCP_NO_IMPLEMENTATION_CLASS_UID,
+    /// Refusing association because of no acceptable Presentation Contexts
+    DCMSCP_NO_PRESENTATION_CONTEXTS,
+    /// Refusing association because of internal error
+    DCMSCP_INTERNAL_ERROR
 };
 
 /** Structure representing a single Presentation Context. Fields "reserved" and "result"
@@ -101,29 +99,28 @@ enum DcmRefuseReasonType
  */
 struct DCMTK_DCMNET_EXPORT DcmPresentationContextInfo
 {
-  DcmPresentationContextInfo()
-    : presentationContextID(0)
-    , abstractSyntax()
-    , proposedSCRole(0)
-    , acceptedSCRole(0)
-    , acceptedTransferSyntax()
-  {
-  }
-
-  /// Presentation Context ID as proposed by SCU
-  Uint8 presentationContextID;
-  /// Abstract Syntax name (UID) as proposed by SCU
-  OFString abstractSyntax;
-  /// SCP role as proposed from SCU
-  Uint8 proposedSCRole;
-  /// Role accepted by SCP for this Presentation Context
-  Uint8 acceptedSCRole;
-  /// Transfer Syntax accepted for this Presentation Context (UID)
-  OFString acceptedTransferSyntax;
-  // Fields "reserved" and "result" not included from DUL_PRESENTATIONCONTEXT
+    DcmPresentationContextInfo()
+        : presentationContextID(0)
+        , abstractSyntax()
+        , proposedSCRole(0)
+        , acceptedSCRole(0)
+        , acceptedTransferSyntax()
+    {
+    }
+
+    /// Presentation Context ID as proposed by SCU
+    Uint8 presentationContextID;
+    /// Abstract Syntax name (UID) as proposed by SCU
+    OFString abstractSyntax;
+    /// SCP role as proposed from SCU
+    Uint8 proposedSCRole;
+    /// Role accepted by SCP for this Presentation Context
+    Uint8 acceptedSCRole;
+    /// Transfer Syntax accepted for this Presentation Context (UID)
+    OFString acceptedTransferSyntax;
+    // Fields "reserved" and "result" not included from DUL_PRESENTATIONCONTEXT
 };
 
-
 /** Base class for implementing a DICOM Service Class Provider (SCP). Derived classes can
  *  add the presentation contexts they want to support, set further parameters (port, peer
  *  host name, etc. as desired) and then call DcmSCP's listen() method to start the server.
@@ -141,1022 +138,1029 @@ class DCMTK_DCMNET_EXPORT DcmSCP
 {
 
 public:
-
-  /** Constructor. Initializes internal member variables.
-   */
-  DcmSCP();
-
-  /** Virtual destructor, frees internal memory.
-   */
-  virtual ~DcmSCP();
-
-  /** Starts providing the implemented services to SCUs.
-   *  After calling this method the SCP is listening for connection requests.
-   *  @return The result. Per default, the method only returns in case of fatal errors.
-   *          However, there are ways to stop listening in a controlled way:
-   *          <ul>
-   *          <li>In non-blocking mode, use stopAfterConnectionTimeout() in order
-   *          shut down after the TCP timeout set with setConnectionTimeout() has
-   *          occurred. In that case, the method returns with NET_EC_StopAfterConnectionTimeout.</li>
-   *          <li>In non-blocking and blocking mode, stopAfterCurrentAssociation() can
-   *          be used to return after an association has been handled and ended.
-   *          In that case, NET_EC_StopAfterAssociation is returned.</li>
-   *          </ul>
-   *         Other error codes include
-   *          <ul>
-   *          <li>NET_EC_InvalidSCPAssociationProfile: Returned if the SCP's presentation
-   *          context information is invalid (e.g. no presentation contexts have
-   *          been added).
-   *          </li>
-   *          <li>NET_EC_InsufficientPortPrivileges: Returned if the SCP is not
-   *          allowed to open the specified TCP port for listening. The reason
-   *          may be that you try to open a port number below 1024 on a Unix-like
-   *          system as non-root user.
-   *          <li>EC_setuidFailed: Returned (on Unix-like systems) if the DcmSCP
-   *          was not able to drop root privileges.
-   *          </ul>
-   */
-  virtual OFCondition listen();
-
-  /* ************************************************************* */
-  /*             Set methods for configuring SCP behavior          */
-  /* ************************************************************* */
-
-  /** Enables negotiation of the Verification SOP Class. It adds the Verification
-   *  SOP Class to the list of supported abstract syntaxes for the given profile.
-   *  All uncompressed transfer syntaxes are supported. If Verification SOP
-   *  class is added here, DcmSCP will respond to related C-ECHO requests. Note
-   *  that this cannot be reverted.
-   *  The default behavior of DcmSCP is not to support any SOP Class at all.
-   *  @param profile [in] The profile Verification SOP Class should
-   *                 be added to. The default is to add it to the
-   *                 DcmSCP's internal standard profile called
-   *                 "DEFAULT".
-   *  @return EC_Normal if Verification SOP Class could be added,
-   *          error otherwise.
-   */
-  OFCondition setEnableVerification(const OFString& profile="DEFAULT");
-
-  /** Add abstract syntax to presentation contexts the SCP is able to negotiate with SCUs.
-   *  @param abstractSyntax [in] The UID of the abstract syntax (e.g.\ SOP class) to add
-   *  @param xferSyntaxes   [in] List of transfer syntaxes (UIDs) that should be supported
-   *                             for the given abstract syntax name
-   *  @param requestorRole  [in] The role to be negotiated. This denotes the role of the
-   *                        the association requestor that this instance should accept, i.e. if
-   *                        set to ASC_SC_ROLE_SCP it means that the association requestor
-   *                        is allowed to negotiate the SCP role, thus, that this DcmSCP instance
-   *                        will be playing the SCU role for this abstract syntax. The default
-   *                        role (ASC_SC_ROLE_DEFAULT) implicates that this DcmSCP instance
-   *                        will be allowed to play the SCP role only, i.e. it will acknowledge
-   *                        such an explicit SCU role request, but also it will accept a proposal
-   *                        for the abstract syntax with no explicit role being proposed
-   *                        at all (since per default the requestor is SCU and the acceptor SCP).
-   *  @param profile        [in] The profile the abstract syntax should be added to. The
-   *                             default is to add it to the DcmSCP's internal standard
-   *                             profile called "DEFAULT".
-   *  @return EC_Normal if adding was successful, an error code otherwise
-   */
-  virtual OFCondition addPresentationContext(const OFString &abstractSyntax,
-                                             const OFList<OFString> &xferSyntaxes,
-                                             const T_ASC_SC_ROLE requestorRole = ASC_SC_ROLE_DEFAULT,
-                                             const OFString &profile = "DEFAULT");
-
-  /** Set SCP's TCP/IP listening port
-   *  @param port [in] The port number to listen on. Note that usually on Unix-like systems
-   *                   only root user is permitted to open ports below 1024.
-   */
-  void setPort(const Uint16 port);
-
-  /** Set AE title of the server
-   *  @param aetitle [in] The AE title of the server. By default, all SCU association requests
-   *                      calling another AE title will be rejected. This behavior can be
-   *                      changed by using the setRespondWithCalledAETitle() method.
-   */
-  void setAETitle(const OFString &aetitle);
-
-  /** Set SCP to use the called AE title from the SCU request for the response, i.e.\ the SCP
-   *  will always respond with setting it's own name to the one the SCU used for calling.
-   *  Overrides any AE title eventually set with setAETitle().
-   *  @param useCalled [in] If OFTrue, the SCP will use the called AE title from the request
-   *                        for responding. DcmSCP's default is OFFalse.
-   */
-  void setRespondWithCalledAETitle(const OFBool useCalled);
-
-  /** Loads association configuration file
-   *  @param assocFile [in] The filename of the association configuration to be loaded. The
-   *                        association configuration file must be valid for an SCP.
-   *  @return EC_Normal if loading was successful, error otherwise
-   */
-  virtual OFCondition loadAssociationCfgFile(const OFString &assocFile);
-
-  /** If an association profile should be selected, either by loading an association
-   *  configuration file or using the addPresentationContext() function, one of those can
-   *  be selected and checked for validity using this method.
-   *  @param profileName [in] The name of the association profile which must be configured
-   *                          before being selected here
-   *  @return EC_Normal if selecting/checking was successful, an error code otherwise
-   */
-  virtual OFCondition setAndCheckAssociationProfile(const OFString &profileName);
-
-  /** Force every association request to be refused by SCP, no matter what the SCU is
-   *  offering
-   *  @param doRefuse [in] If OFTrue, every association is being refused. DcmSCP's default
-   *                       is not to refuse every association.
-   */
-  void forceAssociationRefuse(const OFBool doRefuse);
-
-  /** Set maximum PDU size the SCP is able to receive. This size is sent in association
-   *  response message to SCU.
-   *  @param maxRecPDU [in] The maximum PDU size to use in bytes
-   */
-  void setMaxReceivePDULength(const Uint32 maxRecPDU);
-
-  /** Set whether waiting for a TCP/IP connection should be blocking or non-blocking.
-   *  In non-blocking mode, the networking routines will wait for specified connection
-   *  timeout, see setConnectionTimeout() function. In blocking mode, no timeout is set
-   *  but the operating system's network routines will be used to read from the socket
-   *  for incoming data. In the worst case, this may be a long time until that call
-   *  returns. The default of DcmSCP is blocking mode.
-   *  @param blockingMode [in] Either DUL_BLOCK for blocking mode or DUL_NOBLOCK
-   *                           for non-blocking mode
-   */
-  void setConnectionBlockingMode(const DUL_BLOCKOPTIONS blockingMode);
-
-  /** Set whether DIMSE messaging should be blocking or non-blocking. In non-blocking mode,
-   *  the networking routines will wait for DIMSE messages for the specified DIMSE timeout
-   *  time, see setDIMSETimeout() function. In blocking mode, no timeout is set but the
-   *  operating system's network routines will be used to read from the socket for new data.
-   *  In the worst case, this may be a long time until that call returns. The default of
-   *  DcmSCP is blocking mode.
-   *  @param blockingMode [in] Either DIMSE_BLOCKING for blocking mode or DIMSE_NONBLOCKING
-   *                           for non-blocking mode
-   */
-  void setDIMSEBlockingMode(const T_DIMSE_BlockingMode blockingMode);
-
-  /** Set the timeout to be waited for incoming DIMSE message packets. This is only relevant
-   *  for DIMSE blocking mode messaging (see also setDIMSEBlockingMode()).
-   *  @param dimseTimeout [in] DIMSE receive timeout in seconds
-   */
-  void setDIMSETimeout(const Uint32 dimseTimeout);
-
-  /** Set the timeout used during ACSE messaging protocol.
-   *  @param acseTimeout [in] ACSE timeout in seconds.
-   */
-  void setACSETimeout(const Uint32 acseTimeout);
-
-  /** Set the timeout that should be waited for connection requests.
-   *  Only relevant in non-blocking mode (default).
-   *  @param timeout [in] TCP/IP connection timeout in seconds.
-   */
-  void setConnectionTimeout(const Uint32 timeout);
-
-  /** Set whether to show presentation contexts in verbose or debug mode
-   *  @param mode [in] Show presentation contexts in verbose mode if OFTrue. By default, the
-   *                   presentation contexts are shown in debug mode.
-   */
-  void setVerbosePCMode(const OFBool mode);
-
-  /** Enables or disables looking up the host name from a connecting system.
-   *  Note that this sets a GLOBAL flag in DCMTK, i.e. the behavior changes
-   *  for all servers. This should be changed in the future.
-   *  @param mode [in] OFTrue, if host name lookup should be enabled, OFFalse for disabling it.
-   */
-  void setHostLookupEnabled(const OFBool mode);
-
-  /** Set the mode that specifies whether the progress of sending and receiving DIMSE messages
-   *  is notified by calling notifySENDProgress() and notifyRECEIVEProgress(), respectively.
-   *  The progress notification is enabled by default.
-   *  @param mode [in] Disable progress notification if OFFalse
-   */
-  void setProgressNotificationMode(const OFBool mode);
-
-  /** Option to always accept a default role as association acceptor.
-   *  If OFFalse (default) the acceptor will reject a presentation context proposed
-   *  with Default role (no role selection at all) when it is configured for role
-   *  SCP only. If this option is set to OFTrue then such presentation contexts will
-   *  be accepted in Default role (i.e. acceptor does not return role selection for
-   *  this presentation context at all). Overall, if set to OFTrue, there are no
-   *  requestor proposals possible that lead to a complete rejection of a presentation
-   *  context. See also role documentation in dul.h.
-   *  @param  enabled If OFTrue, do not reject Default role proposals when configured
-   *          for SCP role. OFFalse (default behaviour): Reject such proposals.
-   */
-  void setAlwaysAcceptDefaultRole(const OFBool enabled);
-
-  /* Get methods for SCP settings */
-
-  /** Returns TCP/IP port number SCP listens for new connection requests
-   *  @return The port number
-   */
-  Uint16 getPort() const;
-
-  /** Returns SCP's own AE title. Only used if the SCP is not configured to respond with the
-   *  called AE title the SCU uses for association negotiation, see setRespondWithCalledAETitle().
-   *  @return The configured AE title
-   */
-  const OFString &getAETitle() const;
-
-  /** Returns whether SCP uses the called AE title from SCU requests to respond to connection
-   *  requests instead of a configured AE title
-   *  @return OFTrue, if the SCU's calling AE title is utilized, OFFalse otherwise
-   */
-  OFBool getRespondWithCalledAETitle() const;
-
-  /** Returns whether SCP should refuse any association request no matter what the SCU proposes
-   *  @return OFTrue, if SCP is configured to refuse every association
-   */
-  OFBool getRefuseAssociation() const;
-
-  /** Returns maximum PDU length configured to be received by SCP
-   *  @return Maximum PDU length in bytes
-   */
-  Uint32 getMaxReceivePDULength() const;
-
-  /** Returns whether receiving of TCP/IP connection requests is done in blocking or
-   *  unblocking mode
-   *  @return DUL_BLOCK if in blocking mode, otherwise DUL_NOBLOCK
-   */
-  DUL_BLOCKOPTIONS getConnectionBlockingMode() const;
-
-  /** Returns whether receiving of DIMSE messages is done in blocking or unblocking mode
-   *  @return DIMSE_BLOCKING if in blocking mode, otherwise DIMSE_NONBLOCKING
-   */
-  T_DIMSE_BlockingMode getDIMSEBlockingMode() const;
-
-  /** Returns DIMSE timeout (only applicable in blocking mode)
-   *  @return DIMSE timeout in seconds
-   */
-  Uint32 getDIMSETimeout() const;
-
-  /** Returns ACSE timeout
-   *  @return ACSE timeout in seconds
-   */
-  Uint32 getACSETimeout() const;
-
-  /** Returns connection timeout
-   *  @return TCP/IP connection timeout in seconds
-   */
-  Uint32 getConnectionTimeout() const;
-
-  /** Returns the verbose presentation context mode configured specifying whether details on
-   *  the presentation contexts (negotiated during association setup) should be shown in
-   *  verbose or debug mode. The latter is the default.
-   *  @return The verbose presentation context mode configured
-   */
-  OFBool getVerbosePCMode() const;
-
-  /** Returns whether a connecting system's host name is looked up.
-   *  @return OFTrue, if host name lookup is enabled, OFFalse otherwise
-   */
-  OFBool getHostLookupEnabled() const;
-
-  /** Returns the mode that specifies whether the progress of sending and receiving DIMSE
-   *  messages is notified by calling notifySENDProgress() and notifyRECEIVEProgress(),
-   *  respectively. The progress notification is enabled by default.
-   *  @return The current progress notification mode, enabled if OFTrue
-   */
-  OFBool getProgressNotificationMode() const;
-
-  /** Get access to the configuration of the SCP. Note that the functionality
-   *  on the configuration object is shadowed by other API functions of DcmSCP.
-   *  The existing functions are provided in order to not break users of this
-   *  "older" API where no configuration object existed.
-   *  @return a reference to the DcmSCPConfig object used by this DcmSCP object.
-   */
-  virtual DcmSCPConfig& getConfig();
-
-  /** Set the DcmSCPConfig object to use for configuring this DcmSCP object.
-   *  A deep copy is performed.
-   *  @param  config The configuration to use.
-   *  @return EC_Normal if configuration can be used. The configuration can
-   *          only be changed if the SCP is not yet connected, otherwise
-   *          NET_EC_AlreadyConnected is returned.
-   *
-   */
-  virtual OFCondition setConfig(const DcmSCPConfig& config);
-
-  /* ************************************************************* */
-  /*  Methods for receiving runtime (i.e. connection time) infos   */
-  /* ************************************************************* */
-
-  /** Returns whether SCP is currently connected. If in multi-process mode, the "father"
-   *  process should always return false here, because connection is always handled by child
-   *  process.
-   *  @return OFTrue, if SCP is currently connected to calling SCU
-   */
-  OFBool isConnected() const;
-
-  /** Returns number of associations currently running. Only applicable in Unix-like
-   *  operating systems. Can only be greater than one when running in multi-process mode.
-   *  @return Number of currently running associations
-   */
-  Uint16 numAssociations() const;
-
-  /** Returns AE title the SCU used as called AE title in association request
-   *  @return AE title the SCP was called with. Empty string if SCP is currently not
-   *          connected.
-   */
-  OFString getCalledAETitle() const;
-
-  /** Returns AE title (calling AE title) the SCU used for association request
-   *  @return Calling AE title of SCU. Empty string if SCP is currently not connected.
-   */
-  OFString getPeerAETitle() const;
-
-  /** Returns IP address of connected SCU
-   *  @return IP address of connected SCU. Empty string if SCP is currently not connected.
-   */
-  OFString getPeerIP() const;
-
-  /** Returns maximum PDU size the communication peer (i.e.\ the SCU) is able to receive
-   *  @return Maximum PDU size the SCU is able to receive. Returns zero if SCP is currently
-   *          not connected.
-   */
-  Uint32 getPeerMaxPDULength() const;
-
-  /// DcmThreadSCP needs access to configuration (m_cfg), at least
-  friend class DcmThreadSCP;
+    /** Constructor. Initializes internal member variables.
+     */
+    DcmSCP();
+
+    /** Virtual destructor, frees internal memory.
+     */
+    virtual ~DcmSCP();
+
+    /** Starts providing the implemented services to SCUs.
+     *  After calling this method the SCP is listening for connection requests.
+     *  @return The result. Per default, the method only returns in case of fatal errors.
+     *          However, there are ways to stop listening in a controlled way:
+     *          <ul>
+     *          <li>In non-blocking mode, use stopAfterConnectionTimeout() in order
+     *          shut down after the TCP timeout set with setConnectionTimeout() has
+     *          occurred. In that case, the method returns with NET_EC_StopAfterConnectionTimeout.</li>
+     *          <li>In non-blocking and blocking mode, stopAfterCurrentAssociation() can
+     *          be used to return after an association has been handled and ended.
+     *          In that case, NET_EC_StopAfterAssociation is returned.</li>
+     *          </ul>
+     *         Other error codes include
+     *          <ul>
+     *          <li>NET_EC_InvalidSCPAssociationProfile: Returned if the SCP's presentation
+     *          context information is invalid (e.g. no presentation contexts have
+     *          been added).
+     *          </li>
+     *          <li>NET_EC_InsufficientPortPrivileges: Returned if the SCP is not
+     *          allowed to open the specified TCP port for listening. The reason
+     *          may be that you try to open a port number below 1024 on a Unix-like
+     *          system as non-root user.
+     *          <li>EC_setuidFailed: Returned (on Unix-like systems) if the DcmSCP
+     *          was not able to drop root privileges.
+     *          </ul>
+     */
+    virtual OFCondition listen();
+
+    /** Alternative interface to providing the implemented services to SCUs.
+     *  This method opens the TCP port for incoming connections, drops root privileges
+     *  if necessary and then returns. The caller can then perform short other operations
+     *  and finally call acceptAssociations(). If any SCU tries to connect between
+     *  this method and the call to acceptAssociations(), they are placed on the
+     *  TCP listen backlog and will be handled by acceptAssociations() unless they
+     *  time out or the backlog overflows (the size of the backlog is defined by the
+     *  PRV_LISTENBACKLOG macro).
+     *  @return EC_Normal if successful, an error code otherwise.
+     */
+    virtual OFCondition openListenPort();
+
+    /** Alternative interface to providing the implemented services to SCUs.
+     *  This method should be called after a call to openListenPort().
+     *  @return The result. Per default, the method only returns in case of fatal errors.
+     *    See documentation of listen() method on how to stop listening in a controlled way.
+     */
+    virtual OFCondition acceptAssociations();
+
+    /* ************************************************************* */
+    /*             Set methods for configuring SCP behavior          */
+    /* ************************************************************* */
+
+    /** Enables negotiation of the Verification SOP Class. It adds the Verification
+     *  SOP Class to the list of supported abstract syntaxes for the given profile.
+     *  All uncompressed transfer syntaxes are supported. If Verification SOP
+     *  class is added here, DcmSCP will respond to related C-ECHO requests. Note
+     *  that this cannot be reverted.
+     *  The default behavior of DcmSCP is not to support any SOP Class at all.
+     *  @param profile [in] The profile Verification SOP Class should
+     *                 be added to. The default is to add it to the
+     *                 DcmSCP's internal standard profile called
+     *                 "DEFAULT".
+     *  @return EC_Normal if Verification SOP Class could be added,
+     *          error otherwise.
+     */
+    OFCondition setEnableVerification(const OFString& profile = "DEFAULT");
+
+    /** Add abstract syntax to presentation contexts the SCP is able to negotiate with SCUs.
+     *  @param abstractSyntax [in] The UID of the abstract syntax (e.g.\ SOP class) to add
+     *  @param xferSyntaxes   [in] List of transfer syntaxes (UIDs) that should be supported
+     *                             for the given abstract syntax name
+     *  @param requestorRole  [in] The role to be negotiated. This denotes the role of the
+     *                        the association requestor that this instance should accept, i.e. if
+     *                        set to ASC_SC_ROLE_SCP it means that the association requestor
+     *                        is allowed to negotiate the SCP role, thus, that this DcmSCP instance
+     *                        will be playing the SCU role for this abstract syntax. The default
+     *                        role (ASC_SC_ROLE_DEFAULT) implicates that this DcmSCP instance
+     *                        will be allowed to play the SCP role only, i.e. it will acknowledge
+     *                        such an explicit SCU role request, but also it will accept a proposal
+     *                        for the abstract syntax with no explicit role being proposed
+     *                        at all (since per default the requestor is SCU and the acceptor SCP).
+     *  @param profile        [in] The profile the abstract syntax should be added to. The
+     *                             default is to add it to the DcmSCP's internal standard
+     *                             profile called "DEFAULT".
+     *  @return EC_Normal if adding was successful, an error code otherwise
+     */
+    virtual OFCondition addPresentationContext(const OFString& abstractSyntax,
+                                               const OFList<OFString>& xferSyntaxes,
+                                               const T_ASC_SC_ROLE requestorRole = ASC_SC_ROLE_DEFAULT,
+                                               const OFString& profile           = "DEFAULT");
+
+    /** Set SCP's TCP/IP listening port
+     *  @param port [in] The port number to listen on. Note that usually on Unix-like systems
+     *                   only root user is permitted to open ports below 1024.
+     */
+    void setPort(const Uint16 port);
+
+    /** Set AE title of the server
+     *  @param aetitle [in] The AE title of the server. By default, all SCU association requests
+     *                      calling another AE title will be rejected. This behavior can be
+     *                      changed by using the setRespondWithCalledAETitle() method.
+     */
+    void setAETitle(const OFString& aetitle);
+
+    /** Set SCP to use the called AE title from the SCU request for the response, i.e.\ the SCP
+     *  will always respond with setting it's own name to the one the SCU used for calling.
+     *  Overrides any AE title eventually set with setAETitle().
+     *  @param useCalled [in] If OFTrue, the SCP will use the called AE title from the request
+     *                        for responding. DcmSCP's default is OFFalse.
+     */
+    void setRespondWithCalledAETitle(const OFBool useCalled);
+
+    /** Loads association configuration file
+     *  @param assocFile [in] The filename of the association configuration to be loaded. The
+     *                        association configuration file must be valid for an SCP.
+     *  @return EC_Normal if loading was successful, error otherwise
+     */
+    virtual OFCondition loadAssociationCfgFile(const OFString& assocFile);
+
+    /** If an association profile should be selected, either by loading an association
+     *  configuration file or using the addPresentationContext() function, one of those can
+     *  be selected and checked for validity using this method.
+     *  @param profileName [in] The name of the association profile which must be configured
+     *                          before being selected here
+     *  @return EC_Normal if selecting/checking was successful, an error code otherwise
+     */
+    virtual OFCondition setAndCheckAssociationProfile(const OFString& profileName);
+
+    /** Force every association request to be refused by SCP, no matter what the SCU is
+     *  offering
+     *  @param doRefuse [in] If OFTrue, every association is being refused. DcmSCP's default
+     *                       is not to refuse every association.
+     */
+    void forceAssociationRefuse(const OFBool doRefuse);
+
+    /** Set maximum PDU size the SCP is able to receive. This size is sent in association
+     *  response message to SCU.
+     *  @param maxRecPDU [in] The maximum PDU size to use in bytes
+     */
+    void setMaxReceivePDULength(const Uint32 maxRecPDU);
+
+    /** Set whether waiting for a TCP/IP connection should be blocking or non-blocking.
+     *  In non-blocking mode, the networking routines will wait for specified connection
+     *  timeout, see setConnectionTimeout() function. In blocking mode, no timeout is set
+     *  but the operating system's network routines will be used to read from the socket
+     *  for incoming data. In the worst case, this may be a long time until that call
+     *  returns. The default of DcmSCP is blocking mode.
+     *  @param blockingMode [in] Either DUL_BLOCK for blocking mode or DUL_NOBLOCK
+     *                           for non-blocking mode
+     */
+    void setConnectionBlockingMode(const DUL_BLOCKOPTIONS blockingMode);
+
+    /** Set whether DIMSE messaging should be blocking or non-blocking. In non-blocking mode,
+     *  the networking routines will wait for DIMSE messages for the specified DIMSE timeout
+     *  time, see setDIMSETimeout() function. In blocking mode, no timeout is set but the
+     *  operating system's network routines will be used to read from the socket for new data.
+     *  In the worst case, this may be a long time until that call returns. The default of
+     *  DcmSCP is blocking mode.
+     *  @param blockingMode [in] Either DIMSE_BLOCKING for blocking mode or DIMSE_NONBLOCKING
+     *                           for non-blocking mode
+     */
+    void setDIMSEBlockingMode(const T_DIMSE_BlockingMode blockingMode);
+
+    /** Set the timeout to be waited for incoming DIMSE message packets. This is only relevant
+     *  for DIMSE blocking mode messaging (see also setDIMSEBlockingMode()).
+     *  @param dimseTimeout [in] DIMSE receive timeout in seconds
+     */
+    void setDIMSETimeout(const Uint32 dimseTimeout);
+
+    /** Set the timeout used during ACSE messaging protocol.
+     *  @param acseTimeout [in] ACSE timeout in seconds.
+     */
+    void setACSETimeout(const Uint32 acseTimeout);
+
+    /** Set the timeout that should be waited for connection requests.
+     *  Only relevant in non-blocking mode (default).
+     *  @param timeout [in] TCP/IP connection timeout in seconds.
+     */
+    void setConnectionTimeout(const Uint32 timeout);
+
+    /** Set whether to show presentation contexts in verbose or debug mode
+     *  @param mode [in] Show presentation contexts in verbose mode if OFTrue. By default, the
+     *                   presentation contexts are shown in debug mode.
+     */
+    void setVerbosePCMode(const OFBool mode);
+
+    /** Enables or disables looking up the host name from a connecting system.
+     *  Note that this sets a GLOBAL flag in DCMTK, i.e. the behavior changes
+     *  for all servers. This should be changed in the future.
+     *  @param mode [in] OFTrue, if host name lookup should be enabled, OFFalse for disabling it.
+     */
+    void setHostLookupEnabled(const OFBool mode);
+
+    /** Set the mode that specifies whether the progress of sending and receiving DIMSE messages
+     *  is notified by calling notifySENDProgress() and notifyRECEIVEProgress(), respectively.
+     *  The progress notification is enabled by default.
+     *  @param mode [in] Disable progress notification if OFFalse
+     */
+    void setProgressNotificationMode(const OFBool mode);
+
+    /** Option to always accept a default role as association acceptor.
+     *  If OFFalse (default) the acceptor will reject a presentation context proposed
+     *  with Default role (no role selection at all) when it is configured for role
+     *  SCP only. If this option is set to OFTrue then such presentation contexts will
+     *  be accepted in Default role (i.e. acceptor does not return role selection for
+     *  this presentation context at all). Overall, if set to OFTrue, there are no
+     *  requestor proposals possible that lead to a complete rejection of a presentation
+     *  context. See also role documentation in dul.h.
+     *  @param  enabled If OFTrue, do not reject Default role proposals when configured
+     *          for SCP role. OFFalse (default behaviour): Reject such proposals.
+     */
+    void setAlwaysAcceptDefaultRole(const OFBool enabled);
+
+    /* Get methods for SCP settings */
+
+    /** Returns TCP/IP port number SCP listens for new connection requests
+     *  @return The port number
+     */
+    Uint16 getPort() const;
+
+    /** Returns SCP's own AE title. Only used if the SCP is not configured to respond with the
+     *  called AE title the SCU uses for association negotiation, see setRespondWithCalledAETitle().
+     *  @return The configured AE title
+     */
+    const OFString& getAETitle() const;
+
+    /** Returns whether SCP uses the called AE title from SCU requests to respond to connection
+     *  requests instead of a configured AE title
+     *  @return OFTrue, if the SCU's calling AE title is utilized, OFFalse otherwise
+     */
+    OFBool getRespondWithCalledAETitle() const;
+
+    /** Returns whether SCP should refuse any association request no matter what the SCU proposes
+     *  @return OFTrue, if SCP is configured to refuse every association
+     */
+    OFBool getRefuseAssociation() const;
+
+    /** Returns maximum PDU length configured to be received by SCP
+     *  @return Maximum PDU length in bytes
+     */
+    Uint32 getMaxReceivePDULength() const;
+
+    /** Returns whether receiving of TCP/IP connection requests is done in blocking or
+     *  unblocking mode
+     *  @return DUL_BLOCK if in blocking mode, otherwise DUL_NOBLOCK
+     */
+    DUL_BLOCKOPTIONS getConnectionBlockingMode() const;
+
+    /** Returns whether receiving of DIMSE messages is done in blocking or unblocking mode
+     *  @return DIMSE_BLOCKING if in blocking mode, otherwise DIMSE_NONBLOCKING
+     */
+    T_DIMSE_BlockingMode getDIMSEBlockingMode() const;
+
+    /** Returns DIMSE timeout (only applicable in blocking mode)
+     *  @return DIMSE timeout in seconds
+     */
+    Uint32 getDIMSETimeout() const;
+
+    /** Returns ACSE timeout
+     *  @return ACSE timeout in seconds
+     */
+    Uint32 getACSETimeout() const;
+
+    /** Returns connection timeout
+     *  @return TCP/IP connection timeout in seconds
+     */
+    Uint32 getConnectionTimeout() const;
+
+    /** Returns the verbose presentation context mode configured specifying whether details on
+     *  the presentation contexts (negotiated during association setup) should be shown in
+     *  verbose or debug mode. The latter is the default.
+     *  @return The verbose presentation context mode configured
+     */
+    OFBool getVerbosePCMode() const;
+
+    /** Returns whether a connecting system's host name is looked up.
+     *  @return OFTrue, if host name lookup is enabled, OFFalse otherwise
+     */
+    OFBool getHostLookupEnabled() const;
+
+    /** Returns the mode that specifies whether the progress of sending and receiving DIMSE
+     *  messages is notified by calling notifySENDProgress() and notifyRECEIVEProgress(),
+     *  respectively. The progress notification is enabled by default.
+     *  @return The current progress notification mode, enabled if OFTrue
+     */
+    OFBool getProgressNotificationMode() const;
+
+    /** Get access to the configuration of the SCP. Note that the functionality
+     *  on the configuration object is shadowed by other API functions of DcmSCP.
+     *  The existing functions are provided in order to not break users of this
+     *  "older" API where no configuration object existed.
+     *  @return a reference to the DcmSCPConfig object used by this DcmSCP object.
+     */
+    virtual DcmSCPConfig& getConfig();
+
+    /** Set the DcmSCPConfig object to use for configuring this DcmSCP object.
+     *  A deep copy is performed.
+     *  @param  config The configuration to use.
+     *  @return EC_Normal if configuration can be used. The configuration can
+     *          only be changed if the SCP is not yet connected, otherwise
+     *          NET_EC_AlreadyConnected is returned.
+     *
+     */
+    virtual OFCondition setConfig(const DcmSCPConfig& config);
+
+    /* ************************************************************* */
+    /*  Methods for receiving runtime (i.e. connection time) infos   */
+    /* ************************************************************* */
+
+    /** Returns whether SCP is currently connected. If in multi-process mode, the "father"
+     *  process should always return false here, because connection is always handled by child
+     *  process.
+     *  @return OFTrue, if SCP is currently connected to calling SCU
+     */
+    OFBool isConnected() const;
+
+    /** Returns number of associations currently running. Only applicable in Unix-like
+     *  operating systems. Can only be greater than one when running in multi-process mode.
+     *  @return Number of currently running associations
+     */
+    Uint16 numAssociations() const;
+
+    /** Returns AE title the SCU used as called AE title in association request
+     *  @return AE title the SCP was called with. Empty string if SCP is currently not
+     *          connected.
+     */
+    OFString getCalledAETitle() const;
+
+    /** Returns AE title (calling AE title) the SCU used for association request
+     *  @return Calling AE title of SCU. Empty string if SCP is currently not connected.
+     */
+    OFString getPeerAETitle() const;
+
+    /** Returns IP address of connected SCU
+     *  @return IP address of connected SCU. Empty string if SCP is currently not connected.
+     */
+    OFString getPeerIP() const;
+
+    /** Returns maximum PDU size the communication peer (i.e.\ the SCU) is able to receive
+     *  @return Maximum PDU size the SCU is able to receive. Returns zero if SCP is currently
+     *          not connected.
+     */
+    Uint32 getPeerMaxPDULength() const;
+
+    /// DcmThreadSCP needs access to configuration (m_cfg), at least
+    friend class DcmThreadSCP;
 
 protected:
-
-  /* ********************************************* */
-  /*  Functions available to derived classes only  */
-  /* ********************************************* */
-
-  /** This call returns the presentation context belonging to the given
-   *  presentation context ID.
-   *  @param presID         [in]  The presentation context ID to look for
-   *  @param abstractSyntax [out] The abstract syntax (UID) for that ID.
-   *                              Empty, if such a presentation context does not exist.
-   *  @param transferSyntax [out] The transfer syntax (UID) for that ID.
-   *                              Empty, if such a presentation context does not exist.
-   */
-  void findPresentationContext(const T_ASC_PresentationContextID presID,
-                               OFString &abstractSyntax,
-                               OFString &transferSyntax);
-
-  /** Aborts the current association by sending an A-ABORT request to the SCU.
-   *  This method allows derived classes to abort an association in case of severe errors.
-   *  @return status, EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition abortAssociation();
-
-  /* *********************************************************************** */
-  /*  Functions particularly interesting for overwriting in derived classes  */
-  /* *********************************************************************** */
-
-  /** Handle incoming command set and react accordingly, e.g.\ sending response via
-   *  DIMSE_sendXXXResponse(). The standard handler only knows how to handle
-   *  a C-ECHO request message (by calling handleEchoRequest()) if it is sent on a
-   *  presentation context configured for the Verification SOP Class.
-   *  This function is most likely to be implemented by a derived class
-   *  implementing a specific SCP behavior.
-   *  @param incomingMsg The DIMSE message received
-   *  @param presInfo Additional information on the Presentation Context used
-   *  @return EC_Normal if the message could be handled, error if not. Especially
-   *          DIMSE_BADCOMMANDTYPE should be returned if there is no handler for
-   *          this particular type of DIMSE message. E.g. the default handler in
-   *          DcmSCP only handles C-ECHO requests and, therefore, returns
-   *          DIMSE_BADCOMMANDTYPE otherwise.
-   */
-  virtual OFCondition handleIncomingCommand(T_DIMSE_Message *incomingMsg,
-                                            const DcmPresentationContextInfo &presInfo);
-
-  /** Overwrite this function to be notified about an incoming association request.
-   *  The standard handler only outputs some information to the logger.
-   *  @param params The association parameters that were received.
-   *  @param desiredAction The desired action how to handle this association request.
-   */
-  virtual void notifyAssociationRequest(const T_ASC_Parameters &params,
-                                        DcmSCPActionType &desiredAction);
-
-  /** Overwrite this function if called AE title should undergo checking. If
-   *  OFTrue is returned, the AE title is accepted and processing is continued.
-   *  In case of OFFalse, the SCP will refuse the incoming association with
-   *  error "Called Application Entity Title Not Recognized".
-   *  The standard handler always returns OFTrue.
-   *  @param calledAE The called AE title the SCU used that should be checked
-   *  @return OFTrue, if AE title is accepted, OFFalse otherwise
-   */
-  virtual OFBool checkCalledAETitleAccepted(const OFString& calledAE);
-
-  /** Overwrite this function if calling AE title should undergo checking. If
-   *  OFTrue is returned, the AE title is accepted and processing is continued.
-   *  In case of OFFalse, the SCP will refuse the incoming association with
-   *  error "Calling Application Entity Title Not Recognized".
-   *  The standard handler always returns OFTrue.
-   *  @param callingAE The calling AE title the SCU used that should be checked
-   *  @return OFTrue, if AE title is accepted, OFFalse otherwise
-   */
-  virtual OFBool checkCallingAETitleAccepted(const OFString& callingAE);
-
-  /** Overwrite this function if calling IP / host name should undergo checking.
-   *  If OFTrue is returned, the host is accepted and processing is continued.
-   *  In case of OFFalse, the SCP will refuse the incoming association with
-   *  an error. The standard handler always returns OFTrue.
-   *  @param hostOrIP The IP of the client to check.
-   *  @return OFTrue, if IP/host is accepted, OFFalse otherwise
-   */
-  virtual OFBool checkCallingHostAccepted(const OFString& hostOrIP);
-
-  /** Overwrite this function to be notified about an incoming association request.
-   *  The standard handler only outputs some information to the logger.
-   */
-  virtual void notifyAssociationAcknowledge();
-
-  /** Overwrite this function to be notified about an incoming association release request.
-   *  The standard handler only outputs some information to the logger.
-   */
-  virtual void notifyReleaseRequest();
-
-  /** Overwrite this function to be notified about an incoming association abort request.
-   *  The standard handler only outputs some information to the logger.
-   */
-  virtual void notifyAbortRequest();
-
-  /** Overwrite this function to be notified when an association is terminated.
-   *  The standard handler only outputs some information to the logger.
-   */
-  virtual void notifyAssociationTermination();
-
-  /** Overwrite this function to be notified about a connection timeout in
-   *  non-blocking mode (see setConnectionBlockingMode() and setConnectionTimeout()
-   *  methods). In blocking mode, this method has no effect since it's never called.
-   *  The standard handler only outputs some information to the TRACE logger.
-   */
-  virtual void notifyConnectionTimeout();
-
-  /** Overwrite this function to be notified when a DIMSE error occurs.
-   *  The standard handler only outputs error information to the logger.
-   *  @param cond [in] The DIMSE error occurred.
-   */
-  virtual void notifyDIMSEError(const OFCondition &cond);
-
-  /** This function is called while sending DIMSE messages, i.e.\ on each PDV of a dataset.
-   *  The default implementation just prints a TRACE message on the number of bytes sent so
-   *  far. By overwriting this method, the progress of the send process can be shown to the
-   *  user in a more appropriate way. The progress notification can also be disabled
-   *  completely by calling setProgressNotificationMode().
-   *  @param byteCount [in] Number of bytes sent so far
-   */
-  virtual void notifySENDProgress(const unsigned long byteCount);
-
-  /** This function is called while receiving DIMSE messages, i.e.\ on each PDV of a dataset.
-   *  The default implementation just prints a TRACE message on the number of bytes received
-   *  so far. By overwriting this method, the progress of the receive process can be shown to
-   *  the user in a more appropriate way. The progress notification can also be disabled
-   *  completely by calling setProgressNotificationMode().
-   *  @param byteCount [in] Number of bytes received so far
-   */
-  virtual void notifyRECEIVEProgress(const unsigned long byteCount);
-
-  /** This method can be used to return from the listen() loop in a controlled way.
-   *  In order to use it, it must be overwritten in a derived class. As long as no
-   *  severe error occurs and this method returns OFFalse, the listen() method will wait
-   *  for incoming associations in an infinite loop.
-   *  @return The standard handler always returns OFFalse
-   */
-  virtual OFBool stopAfterCurrentAssociation();
-
-  /** This method can be used to return from the listen() loop in a controlled way.
-   *  In order to use it, it must be overwritten in a derived class. As long as no
-   *  severe error occurs and this method returns OFFalse, the listen() method will wait
-   *  for incoming associations in an infinite loop. If this method returns OFTrue, the
-   *  SCP will return from the listen() loop after a connection timeout occurs (see
-   *  setConnectionTimeout() method). In blocking mode (see setConnectionBlockingMode()
-   *  method), this method has no effect (it's never called) since the underlying
-   *  routines will wait forever for an incoming TCP connection.
-   *  @return The standard handler always returns OFFalse
-   */
-  virtual OFBool stopAfterConnectionTimeout();
-
-  // -- C-ECHO --
-
-  /** Standard handler for Verification Service Class (DICOM Echo). Returns echo response
-   *  (i.e. whether C-ECHO could be responded to with status success).
-   *  @param reqMessage [in] The C-ECHO request message that was received
-   *  @param presID     [in] The presentation context to be used. By default, the
-   *                         presentation context of the request is used.
-   *  @return status, EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition handleECHORequest(T_DIMSE_C_EchoRQ &reqMessage,
-                                        const T_ASC_PresentationContextID presID);
-
-  // --- C-STORE --
-
-  /** Receive C-STORE request on the currently opened association, store the
-   *  accompanying dataset in memory and send a corresponding response. Calls
-   *  checkSTORERequest() in order to determine the DIMSE status code to be used for
-   *  the C-STORE response.
-   *  @note This handler receives the dataset belonging the C-STORE request completely
-   *    in memory. If very large datasets are expected, another handler should be
-   *    implemented that calls the receiveSTORERequest() method with a filename.
-   *  @param reqMessage [in]    The C-STORE request message that was received
-   *  @param presID     [in]    The presentation context to be used. By default, the
-   *                            presentation context of the request is used.
-   *  @param reqDataset [inout] Pointer to data structure where the received dataset
-   *                            should be stored. If NULL, a new dataset is created,
-   *                            which has to be deleted by the caller.
-   *  @return status, EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition handleSTORERequest(T_DIMSE_C_StoreRQ &reqMessage,
-                                         const T_ASC_PresentationContextID presID,
-                                         DcmDataset *&reqDataset);
-
-  /** Receive C-STORE request (and store accompanying dataset in memory).
-   *  For very large datasets, the other receiveSTORERequest() method should be used
-   *  because it stores the received dataset directly to file.
-   *  @param reqMessage [in]    The C-STORE request message that was received
-   *  @param presID     [in]    The presentation context to be used. By default, the
-   *                            presentation context of the request is used.
-   *  @param reqDataset [inout] Pointer to data structure where the received dataset
-   *                            should be stored. If NULL, a new dataset is created,
-   *                            which has to be deleted by the caller.
-   *  @return status, EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition receiveSTORERequest(T_DIMSE_C_StoreRQ &reqMessage,
-                                          const T_ASC_PresentationContextID presID,
-                                          DcmDataset *&reqDataset);
-
-  /** Receive C-STORE request (and store accompanying dataset directly to file).
-   *  The dataset is stored exactly as received, i.e. without any conversions.
-   *  @param reqMessage [in] The C-STORE request message that was received
-   *  @param presID     [in] The presentation context to be used. By default, the
-   *                         presentation context of the request is used.
-   *  @param filename   [in] The filename used to store the received dataset
-   *  @return status, EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition receiveSTORERequest(T_DIMSE_C_StoreRQ &reqMessage,
-                                          const T_ASC_PresentationContextID presID,
-                                          const OFString &filename);
-
-  /** Respond to the C-STORE request (with details from the request message)
-   *  @param presID        [in] The presentation context ID to respond to
-   *  @param reqMessage    [in] The C-STORE request that should be responded to
-   *  @param rspStatusCode [in] The response status code. 0 means success,
-   *                            others can found in the DICOM standard.
-   *  @return EC_Normal, if responding was successful, an error code otherwise
-   */
-  virtual OFCondition sendSTOREResponse(const T_ASC_PresentationContextID presID,
-                                        const T_DIMSE_C_StoreRQ &reqMessage,
-                                        const Uint16 rspStatusCode);
-
-  /** Respond to the C-STORE request (with given details)
-   *  @param presID         [in] The presentation context ID to respond to
-   *  @param messageID      [in] The message ID being responded to
-   *  @param sopClassUID    [in] The affected SOP class UID
-   *  @param sopInstanceUID [in] The affected SOP instance UID
-   *  @param rspStatusCode  [in] The response status code. 0 means success,
-   *                             others can found in the DICOM standard.
-   *  @param statusDetail   [in] The status detail of the response (if desired).
-   *  @return EC_Normal, if responding was successful, an error code otherwise
-   */
-  virtual OFCondition sendSTOREResponse(const T_ASC_PresentationContextID presID,
-                                        const Uint16 messageID,
-                                        const OFString &sopClassUID,
-                                        const OFString &sopInstanceUID,
-                                        const Uint16 rspStatusCode,
-                                        DcmDataset *statusDetail = NULL);
-
-  /** Check given C-STORE request and dataset for validity. This method is called by
-   *  handleSTORERequest() before sending the response in order to determine the DIMSE
-   *  status code to be used for the response message.
-   *  @param reqMessage [in] The C-STORE request message data structure
-   *  @param reqDataset [in] The C-STORE request dataset received. Might be NULL.
-   *  @return DIMSE status code to be used for the C-STORE response.
-   *          Always returns STATUS_Success (0). Derived classes should, therefore,
-   *          overwrite this method and return a more appropriate value based on the
-   *          result of the checks performed.
-   */
-  virtual Uint16 checkSTORERequest(T_DIMSE_C_StoreRQ &reqMessage,
-                                   DcmDataset *reqDataset);
-
-  // -- C-FIND --
-
-  /** Receive C-FIND request
-   *  @param reqMessage [in]  The C-FIND request message that was received
-   *  @param presID     [in]  The presentation context to be used. By default, the
-   *                          presentation context of the request is used.
-   *  @param reqDataset [out] Pointer to the dataset received
-   *  @return status, EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition receiveFINDRequest(T_DIMSE_C_FindRQ &reqMessage,
-                                         const T_ASC_PresentationContextID presID,
-                                         DcmDataset *&reqDataset);
-
-  /** Handle C-FIND request. This function is deprecated and will be removed in
-   *  the future. For now it calls receiveFINDRequest() which should be used
-   *  instead.
-   *  @param reqMessage [in]  The C-FIND request message that was received
-   *  @param presID     [in]  The presentation context to be used. By default, the
-   *                          presentation context of the request is used.
-   *  @param reqDataset [out] Pointer to the dataset received
-   *  @return status, EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition handleFINDRequest(T_DIMSE_C_FindRQ &reqMessage,
-                                        const T_ASC_PresentationContextID presID,
-                                        DcmDataset *&reqDataset)
-  {
-    DCMNET_WARN("handleFINDRequest() is deprecated, use receiveFINDRequest() instead");
-    return receiveFINDRequest(reqMessage, presID, reqDataset);
-  }
-
-  /** Respond to the C-FIND request
-   *  @param presID        [in] The presentation context ID to respond to
-   *  @param messageID     [in] The message ID being responded to
-   *  @param sopClassUID   [in] The affected SOP class UID
-   *  @param rspDataset    [in] The response dataset
-   *  @param rspStatusCode [in] The response status code. 0 means success,
-   *                            others can found in the DICOM standard.
-   *  @param statusDetail  [in] Any status (must fit response code), if desired
-   *  @return EC_Normal, if responding was successful, an error code otherwise
-   */
-  virtual OFCondition sendFINDResponse(const T_ASC_PresentationContextID presID,
-                                       const Uint16 messageID,
-                                       const OFString &sopClassUID,
-                                       DcmDataset *rspDataset,
-                                       const Uint16 rspStatusCode,
-                                       DcmDataset* statusDetail = NULL);
-
-  /** Check for C-CANCEL. This is needed for example for a Query/Retrieve
-   *  server that is in the middle of returning C-FIND responses to a
-   *  client and has to perform a regular check whether the client sent a
-   *  C-CANCEL in order to stop receiving C-FIND responses.
-   *  @param presID    [in] The presentation context ID where C-CANCEL is
-   *                        expected.
-   *  @param messageID [in] The "message ID responded to" that the client
-   *                        is expected to use (usually this is the message
-   *                        ID used in the original FIND/GET/MOVE request).
-   *  @return EC_Normal, if C-CANCEL was received. DIMSE_NODATAAVAILABLE if no
-   *          DIMSE message (or anything) was received from the client.
-   *          DIMSEC_UNEXPECTEDREQUEST if command is received but it is not
-   *          a C-CANCEL message, or the message ID used by client is wrong
-   *          (message ID must be the one from the original FIND/MOVE/GET
-   *          request).
-   *          DIMSEC_INVALIDPRESENTATIONCONTEXTID if the wrong presentation
-   *          context (ID) was used for sending. Other low level errors
-   *          (e.g. DIMSEC_UNEXPECTEDPDVTYPE) could be returned, too.
-   */
-  virtual OFCondition checkForCANCEL(T_ASC_PresentationContextID presID,
-                                     const Uint16 messageID);
-
-  // --- C-MOVE --
-
-  /** Receive C-MOVE request on the currently active association.
-   *  @param reqMessage [in]  The C-MOVE request message that was received
-   *  @param presID     [in]  The presentation context to be used. By default, the
-   *                          presentation context of the request is used.
-   *  @param reqDataset [out] Pointer to the dataset received
-   *  @param moveDest   [out] The move destination where to send the instances
-   *  @return status, EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition receiveMOVERequest(T_DIMSE_C_MoveRQ &reqMessage,
-                                         const T_ASC_PresentationContextID presID,
-                                         DcmDataset *&reqDataset,
-                                         OFString &moveDest);
-
-  /** Receive C-MOVE request on the currently active association. This function
-   *  is deprecated and will be removed in the future. For now it calls
-   *  receiveMOVERequest() which should be used instead.
-   *  @param reqMessage [in]  The C-MOVE request message that was received
-   *  @param presID     [in]  The presentation context to be used. By default, the
-   *                          presentation context of the request is used.
-   *  @param reqDataset [out] Pointer to the dataset received
-   *  @param moveDest   [out] The move destination where to send the instances
-   *  @return status, EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition handleMOVERequest(T_DIMSE_C_MoveRQ &reqMessage,
-                                        const T_ASC_PresentationContextID presID,
-                                        DcmDataset *&reqDataset,
-                                        OFString &moveDest)
-  {
-    DCMNET_WARN("handleMOVERequest() is deprecated, use receiveMOVERequest() instead");
-    return receiveMOVERequest(reqMessage, presID, reqDataset, moveDest);
-  }
-
-  /** Respond to the C-MOVE request
-   *  @param presID        [in] The presentation context ID to respond to
-   *  @param messageID     [in] The message ID being responded to
-   *  @param sopClassUID   [in] The affected SOP class UID
-   *  @param rspDataset    [in] The response dataset
-   *  @param rspStatusCode [in] The status code of the response. 0 means success,
-   *                            others can found in the DICOM standard.
-   *  @param statusDetail  [in] The status detail of the response (if desired).
-   *  @param numRemain     [in] Number of remaining sub-operations.
-   *                            Required for Pending status codes, often optional otherwise.
-   *                            Sent if one of the num parameters is not 0.
-   *  @param numComplete   [in] Number of completed sub-operations.
-   *                            Required for Pending status codes, often optional otherwise.
-   *                            Sent if one of the num parameters is not 0.
-   *  @param numFail       [in] Number of failed sub-operations.
-   *                            Required for Pending status codes, often optional otherwise.
-   *                            Sent if one of the num parameters is not 0.
-   *  @param numWarn       [in] Number of warning sub-operations.
-   *                            Required for Pending status codes, often optional otherwise.
-   *                            Sent if one of the num parameters is not 0.
-   *  @return EC_Normal, if responding was successful, an error code otherwise
-   */
-  virtual OFCondition sendMOVEResponse(const T_ASC_PresentationContextID presID,
-                                       const Uint16 messageID,
-                                       const OFString &sopClassUID,
-                                       DcmDataset *rspDataset,
-                                       const Uint16 rspStatusCode,
-                                       DcmDataset *statusDetail = NULL,
-                                       const Uint16 numRemain = 0,
-                                       const Uint16 numComplete = 0,
-                                       const Uint16 numFail = 0,
-                                       const Uint16 numWarn = 0);
-
-  // -- N-ACTION --
-
-  /** Receive N-ACTION request on the currently opened association.
-   *  @param reqMessage   [in]  The N-ACTION request message that was received
-   *  @param presID       [in]  The presentation context to be used. By default, the
-   *                            presentation context of the request is used.
-   *  @param reqDataset   [out] Pointer to the dataset received
-   *  @param actionTypeID [out] Action Type ID from the command set received
-   *  @return status, EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition receiveACTIONRequest(T_DIMSE_N_ActionRQ &reqMessage,
+    /* ********************************************* */
+    /*  Functions available to derived classes only  */
+    /* ********************************************* */
+
+    /** This call returns the presentation context belonging to the given
+     *  presentation context ID.
+     *  @param presID         [in]  The presentation context ID to look for
+     *  @param abstractSyntax [out] The abstract syntax (UID) for that ID.
+     *                              Empty, if such a presentation context does not exist.
+     *  @param transferSyntax [out] The transfer syntax (UID) for that ID.
+     *                              Empty, if such a presentation context does not exist.
+     */
+    void findPresentationContext(const T_ASC_PresentationContextID presID,
+                                 OFString& abstractSyntax,
+                                 OFString& transferSyntax);
+
+    /** Aborts the current association by sending an A-ABORT request to the SCU.
+     *  This method allows derived classes to abort an association in case of severe errors.
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition abortAssociation();
+
+    /* *********************************************************************** */
+    /*  Functions particularly interesting for overwriting in derived classes  */
+    /* *********************************************************************** */
+
+    /** Handle incoming command set and react accordingly, e.g.\ sending response via
+     *  DIMSE_sendXXXResponse(). The standard handler only knows how to handle
+     *  a C-ECHO request message (by calling handleEchoRequest()) if it is sent on a
+     *  presentation context configured for the Verification SOP Class.
+     *  This function is most likely to be implemented by a derived class
+     *  implementing a specific SCP behavior.
+     *  @param incomingMsg The DIMSE message received
+     *  @param presInfo Additional information on the Presentation Context used
+     *  @return EC_Normal if the message could be handled, error if not. Especially
+     *          DIMSE_BADCOMMANDTYPE should be returned if there is no handler for
+     *          this particular type of DIMSE message. E.g. the default handler in
+     *          DcmSCP only handles C-ECHO requests and, therefore, returns
+     *          DIMSE_BADCOMMANDTYPE otherwise.
+     */
+    virtual OFCondition handleIncomingCommand(T_DIMSE_Message* incomingMsg, const DcmPresentationContextInfo& presInfo);
+
+    /** Overwrite this function to be notified about an incoming association request.
+     *  The standard handler only outputs some information to the logger.
+     *  @param params The association parameters that were received.
+     *  @param desiredAction The desired action how to handle this association request.
+     */
+    virtual void notifyAssociationRequest(const T_ASC_Parameters& params, DcmSCPActionType& desiredAction);
+
+    /** Overwrite this function if called AE title should undergo checking. If
+     *  OFTrue is returned, the AE title is accepted and processing is continued.
+     *  In case of OFFalse, the SCP will refuse the incoming association with
+     *  error "Called Application Entity Title Not Recognized".
+     *  The standard handler always returns OFTrue.
+     *  @param calledAE The called AE title the SCU used that should be checked
+     *  @return OFTrue, if AE title is accepted, OFFalse otherwise
+     */
+    virtual OFBool checkCalledAETitleAccepted(const OFString& calledAE);
+
+    /** Overwrite this function if calling AE title should undergo checking. If
+     *  OFTrue is returned, the AE title is accepted and processing is continued.
+     *  In case of OFFalse, the SCP will refuse the incoming association with
+     *  error "Calling Application Entity Title Not Recognized".
+     *  The standard handler always returns OFTrue.
+     *  @param callingAE The calling AE title the SCU used that should be checked
+     *  @return OFTrue, if AE title is accepted, OFFalse otherwise
+     */
+    virtual OFBool checkCallingAETitleAccepted(const OFString& callingAE);
+
+    /** Overwrite this function if calling IP / host name should undergo checking.
+     *  If OFTrue is returned, the host is accepted and processing is continued.
+     *  In case of OFFalse, the SCP will refuse the incoming association with
+     *  an error. The standard handler always returns OFTrue.
+     *  @param hostOrIP The IP of the client to check.
+     *  @return OFTrue, if IP/host is accepted, OFFalse otherwise
+     */
+    virtual OFBool checkCallingHostAccepted(const OFString& hostOrIP);
+
+    /** Overwrite this function to be notified about an incoming association request.
+     *  The standard handler only outputs some information to the logger.
+     */
+    virtual void notifyAssociationAcknowledge();
+
+    /** Overwrite this function to be notified about an incoming association release request.
+     *  The standard handler only outputs some information to the logger.
+     */
+    virtual void notifyReleaseRequest();
+
+    /** Overwrite this function to be notified about an incoming association abort request.
+     *  The standard handler only outputs some information to the logger.
+     */
+    virtual void notifyAbortRequest();
+
+    /** Overwrite this function to be notified when an association is terminated.
+     *  The standard handler only outputs some information to the logger.
+     */
+    virtual void notifyAssociationTermination();
+
+    /** Overwrite this function to be notified about a connection timeout in
+     *  non-blocking mode (see setConnectionBlockingMode() and setConnectionTimeout()
+     *  methods). In blocking mode, this method has no effect since it's never called.
+     *  The standard handler only outputs some information to the TRACE logger.
+     */
+    virtual void notifyConnectionTimeout();
+
+    /** Overwrite this function to be notified when a DIMSE error occurs.
+     *  The standard handler only outputs error information to the logger.
+     *  @param cond [in] The DIMSE error occurred.
+     */
+    virtual void notifyDIMSEError(const OFCondition& cond);
+
+    /** This function is called while sending DIMSE messages, i.e.\ on each PDV of a dataset.
+     *  The default implementation just prints a TRACE message on the number of bytes sent so
+     *  far. By overwriting this method, the progress of the send process can be shown to the
+     *  user in a more appropriate way. The progress notification can also be disabled
+     *  completely by calling setProgressNotificationMode().
+     *  @param byteCount [in] Number of bytes sent so far
+     */
+    virtual void notifySENDProgress(const unsigned long byteCount);
+
+    /** This function is called while receiving DIMSE messages, i.e.\ on each PDV of a dataset.
+     *  The default implementation just prints a TRACE message on the number of bytes received
+     *  so far. By overwriting this method, the progress of the receive process can be shown to
+     *  the user in a more appropriate way. The progress notification can also be disabled
+     *  completely by calling setProgressNotificationMode().
+     *  @param byteCount [in] Number of bytes received so far
+     */
+    virtual void notifyRECEIVEProgress(const unsigned long byteCount);
+
+    /** This method can be used to return from the listen() loop in a controlled way.
+     *  In order to use it, it must be overwritten in a derived class. As long as no
+     *  severe error occurs and this method returns OFFalse, the listen() method will wait
+     *  for incoming associations in an infinite loop.
+     *  @return The standard handler always returns OFFalse
+     */
+    virtual OFBool stopAfterCurrentAssociation();
+
+    /** This method can be used to return from the listen() loop in a controlled way.
+     *  In order to use it, it must be overwritten in a derived class. As long as no
+     *  severe error occurs and this method returns OFFalse, the listen() method will wait
+     *  for incoming associations in an infinite loop. If this method returns OFTrue, the
+     *  SCP will return from the listen() loop after a connection timeout occurs (see
+     *  setConnectionTimeout() method). In blocking mode (see setConnectionBlockingMode()
+     *  method), this method has no effect (it's never called) since the underlying
+     *  routines will wait forever for an incoming TCP connection.
+     *  @return The standard handler always returns OFFalse
+     */
+    virtual OFBool stopAfterConnectionTimeout();
+
+    // -- C-ECHO --
+
+    /** Standard handler for Verification Service Class (DICOM Echo). Returns echo response
+     *  (i.e. whether C-ECHO could be responded to with status success).
+     *  @param reqMessage [in] The C-ECHO request message that was received
+     *  @param presID     [in] The presentation context to be used. By default, the
+     *                         presentation context of the request is used.
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition handleECHORequest(T_DIMSE_C_EchoRQ& reqMessage, const T_ASC_PresentationContextID presID);
+
+    // --- C-STORE --
+
+    /** Receive C-STORE request on the currently opened association, store the
+     *  accompanying dataset in memory and send a corresponding response. Calls
+     *  checkSTORERequest() in order to determine the DIMSE status code to be used for
+     *  the C-STORE response.
+     *  @note This handler receives the dataset belonging the C-STORE request completely
+     *    in memory. If very large datasets are expected, another handler should be
+     *    implemented that calls the receiveSTORERequest() method with a filename.
+     *  @param reqMessage [in]    The C-STORE request message that was received
+     *  @param presID     [in]    The presentation context to be used. By default, the
+     *                            presentation context of the request is used.
+     *  @param reqDataset [inout] Pointer to data structure where the received dataset
+     *                            should be stored. If NULL, a new dataset is created,
+     *                            which has to be deleted by the caller.
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition handleSTORERequest(T_DIMSE_C_StoreRQ& reqMessage,
+                                           const T_ASC_PresentationContextID presID,
+                                           DcmDataset*& reqDataset);
+
+    /** Receive C-STORE request (and store accompanying dataset in memory).
+     *  For very large datasets, the other receiveSTORERequest() method should be used
+     *  because it stores the received dataset directly to file.
+     *  @param reqMessage [in]    The C-STORE request message that was received
+     *  @param presID     [in]    The presentation context to be used. By default, the
+     *                            presentation context of the request is used.
+     *  @param reqDataset [inout] Pointer to data structure where the received dataset
+     *                            should be stored. If NULL, a new dataset is created,
+     *                            which has to be deleted by the caller.
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition receiveSTORERequest(T_DIMSE_C_StoreRQ& reqMessage,
+                                            const T_ASC_PresentationContextID presID,
+                                            DcmDataset*& reqDataset);
+
+    /** Receive C-STORE request (and store accompanying dataset directly to file).
+     *  The dataset is stored exactly as received, i.e. without any conversions.
+     *  @param reqMessage [in] The C-STORE request message that was received
+     *  @param presID     [in] The presentation context to be used. By default, the
+     *                         presentation context of the request is used.
+     *  @param filename   [in] The filename used to store the received dataset
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition receiveSTORERequest(T_DIMSE_C_StoreRQ& reqMessage,
+                                            const T_ASC_PresentationContextID presID,
+                                            const OFString& filename);
+
+    /** Respond to the C-STORE request (with details from the request message)
+     *  @param presID        [in] The presentation context ID to respond to
+     *  @param reqMessage    [in] The C-STORE request that should be responded to
+     *  @param rspStatusCode [in] The response status code. 0 means success,
+     *                            others can found in the DICOM standard.
+     *  @return EC_Normal, if responding was successful, an error code otherwise
+     */
+    virtual OFCondition sendSTOREResponse(const T_ASC_PresentationContextID presID,
+                                          const T_DIMSE_C_StoreRQ& reqMessage,
+                                          const Uint16 rspStatusCode);
+
+    /** Respond to the C-STORE request (with given details)
+     *  @param presID         [in] The presentation context ID to respond to
+     *  @param messageID      [in] The message ID being responded to
+     *  @param sopClassUID    [in] The affected SOP class UID
+     *  @param sopInstanceUID [in] The affected SOP instance UID
+     *  @param rspStatusCode  [in] The response status code. 0 means success,
+     *                             others can found in the DICOM standard.
+     *  @param statusDetail   [in] The status detail of the response (if desired).
+     *  @return EC_Normal, if responding was successful, an error code otherwise
+     */
+    virtual OFCondition sendSTOREResponse(const T_ASC_PresentationContextID presID,
+                                          const Uint16 messageID,
+                                          const OFString& sopClassUID,
+                                          const OFString& sopInstanceUID,
+                                          const Uint16 rspStatusCode,
+                                          DcmDataset* statusDetail = NULL);
+
+    /** Check given C-STORE request and dataset for validity. This method is called by
+     *  handleSTORERequest() before sending the response in order to determine the DIMSE
+     *  status code to be used for the response message.
+     *  @param reqMessage [in] The C-STORE request message data structure
+     *  @param reqDataset [in] The C-STORE request dataset received. Might be NULL.
+     *  @return DIMSE status code to be used for the C-STORE response.
+     *          Always returns STATUS_Success (0). Derived classes should, therefore,
+     *          overwrite this method and return a more appropriate value based on the
+     *          result of the checks performed.
+     */
+    virtual Uint16 checkSTORERequest(T_DIMSE_C_StoreRQ& reqMessage, DcmDataset* reqDataset);
+
+    // -- C-FIND --
+
+    /** Receive C-FIND request
+     *  @param reqMessage [in]  The C-FIND request message that was received
+     *  @param presID     [in]  The presentation context to be used. By default, the
+     *                          presentation context of the request is used.
+     *  @param reqDataset [out] Pointer to the dataset received
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition
+    receiveFINDRequest(T_DIMSE_C_FindRQ& reqMessage, const T_ASC_PresentationContextID presID, DcmDataset*& reqDataset);
+
+    /** Handle C-FIND request. This function is deprecated and will be removed in
+     *  the future. For now it calls receiveFINDRequest() which should be used
+     *  instead.
+     *  @param reqMessage [in]  The C-FIND request message that was received
+     *  @param presID     [in]  The presentation context to be used. By default, the
+     *                          presentation context of the request is used.
+     *  @param reqDataset [out] Pointer to the dataset received
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition
+    handleFINDRequest(T_DIMSE_C_FindRQ& reqMessage, const T_ASC_PresentationContextID presID, DcmDataset*& reqDataset)
+    {
+        DCMNET_WARN("handleFINDRequest() is deprecated, use receiveFINDRequest() instead");
+        return receiveFINDRequest(reqMessage, presID, reqDataset);
+    }
+
+    /** Respond to the C-FIND request
+     *  @param presID        [in] The presentation context ID to respond to
+     *  @param messageID     [in] The message ID being responded to
+     *  @param sopClassUID   [in] The affected SOP class UID
+     *  @param rspDataset    [in] The response dataset
+     *  @param rspStatusCode [in] The response status code. 0 means success,
+     *                            others can found in the DICOM standard.
+     *  @param statusDetail  [in] Any status (must fit response code), if desired
+     *  @return EC_Normal, if responding was successful, an error code otherwise
+     */
+    virtual OFCondition sendFINDResponse(const T_ASC_PresentationContextID presID,
+                                         const Uint16 messageID,
+                                         const OFString& sopClassUID,
+                                         DcmDataset* rspDataset,
+                                         const Uint16 rspStatusCode,
+                                         DcmDataset* statusDetail = NULL);
+
+    /** Check for C-CANCEL. This is needed for example for a Query/Retrieve
+     *  server that is in the middle of returning C-FIND responses to a
+     *  client and has to perform a regular check whether the client sent a
+     *  C-CANCEL in order to stop receiving C-FIND responses.
+     *  @param presID    [in] The presentation context ID where C-CANCEL is
+     *                        expected.
+     *  @param messageID [in] The "message ID responded to" that the client
+     *                        is expected to use (usually this is the message
+     *                        ID used in the original FIND/GET/MOVE request).
+     *  @return EC_Normal, if C-CANCEL was received. DIMSE_NODATAAVAILABLE if no
+     *          DIMSE message (or anything) was received from the client.
+     *          DIMSEC_UNEXPECTEDREQUEST if command is received but it is not
+     *          a C-CANCEL message, or the message ID used by client is wrong
+     *          (message ID must be the one from the original FIND/MOVE/GET
+     *          request).
+     *          DIMSEC_INVALIDPRESENTATIONCONTEXTID if the wrong presentation
+     *          context (ID) was used for sending. Other low level errors
+     *          (e.g. DIMSEC_UNEXPECTEDPDVTYPE) could be returned, too.
+     */
+    virtual OFCondition checkForCANCEL(T_ASC_PresentationContextID presID, const Uint16 messageID);
+
+    // --- C-MOVE --
+
+    /** Receive C-MOVE request on the currently active association.
+     *  @param reqMessage [in]  The C-MOVE request message that was received
+     *  @param presID     [in]  The presentation context to be used. By default, the
+     *                          presentation context of the request is used.
+     *  @param reqDataset [out] Pointer to the dataset received
+     *  @param moveDest   [out] The move destination where to send the instances
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition receiveMOVERequest(T_DIMSE_C_MoveRQ& reqMessage,
                                            const T_ASC_PresentationContextID presID,
-                                           DcmDataset *&reqDataset,
-                                           Uint16 &actionTypeID);
-
-  /** Receive N-ACTION request on the currently opened association. This
-   *  function is deprecated and will be removed in the future. For now it calls
-   *  receiveACTIONRequest() which should be used instead.
-   *  @param reqMessage   [in]  The N-ACTION request message that was received
-   *  @param presID       [in]  The presentation context to be used. By default, the
-   *                            presentation context of the request is used.
-   *  @param reqDataset   [out] Pointer to the dataset received
-   *  @param actionTypeID [out] Action Type ID from the command set received
-   *  @return status, EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition handleACTIONRequest(T_DIMSE_N_ActionRQ &reqMessage,
+                                           DcmDataset*& reqDataset,
+                                           OFString& moveDest);
+
+    /** Receive C-MOVE request on the currently active association. This function
+     *  is deprecated and will be removed in the future. For now it calls
+     *  receiveMOVERequest() which should be used instead.
+     *  @param reqMessage [in]  The C-MOVE request message that was received
+     *  @param presID     [in]  The presentation context to be used. By default, the
+     *                          presentation context of the request is used.
+     *  @param reqDataset [out] Pointer to the dataset received
+     *  @param moveDest   [out] The move destination where to send the instances
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition handleMOVERequest(T_DIMSE_C_MoveRQ& reqMessage,
                                           const T_ASC_PresentationContextID presID,
-                                          DcmDataset *&reqDataset,
-                                          Uint16 &actionTypeID)
-  {
-    DCMNET_WARN("handleACTIONRequest() is deprecated, use receiveACTIONRequest() instead");
-    return receiveACTIONRequest(reqMessage, presID, reqDataset, actionTypeID);
-  }
-
-  /** Respond to the N-ACTION request
-   *  @param presID         [in] The presentation context ID to respond to
-   *  @param messageID      [in] The message ID being responded to
-   *  @param sopClassUID    [in] The affected SOP class UID
-   *  @param sopInstanceUID [in] The affected SOP instance UID
-   *  @param rspStatusCode  [in] The response status code. 0 means success,
-   *                             others can found in the DICOM standard.
-   *  @return EC_Normal, if responding was successful, an error code otherwise
-   */
-  virtual OFCondition sendACTIONResponse(const T_ASC_PresentationContextID presID,
+                                          DcmDataset*& reqDataset,
+                                          OFString& moveDest)
+    {
+        DCMNET_WARN("handleMOVERequest() is deprecated, use receiveMOVERequest() instead");
+        return receiveMOVERequest(reqMessage, presID, reqDataset, moveDest);
+    }
+
+    /** Respond to the C-MOVE request
+     *  @param presID        [in] The presentation context ID to respond to
+     *  @param messageID     [in] The message ID being responded to
+     *  @param sopClassUID   [in] The affected SOP class UID
+     *  @param rspDataset    [in] The response dataset
+     *  @param rspStatusCode [in] The status code of the response. 0 means success,
+     *                            others can found in the DICOM standard.
+     *  @param statusDetail  [in] The status detail of the response (if desired).
+     *  @param numRemain     [in] Number of remaining sub-operations.
+     *                            Required for Pending status codes, often optional otherwise.
+     *                            Sent if one of the num parameters is not 0.
+     *  @param numComplete   [in] Number of completed sub-operations.
+     *                            Required for Pending status codes, often optional otherwise.
+     *                            Sent if one of the num parameters is not 0.
+     *  @param numFail       [in] Number of failed sub-operations.
+     *                            Required for Pending status codes, often optional otherwise.
+     *                            Sent if one of the num parameters is not 0.
+     *  @param numWarn       [in] Number of warning sub-operations.
+     *                            Required for Pending status codes, often optional otherwise.
+     *                            Sent if one of the num parameters is not 0.
+     *  @return EC_Normal, if responding was successful, an error code otherwise
+     */
+    virtual OFCondition sendMOVEResponse(const T_ASC_PresentationContextID presID,
                                          const Uint16 messageID,
-                                         const OFString &sopClassUID,
-                                         const OFString &sopInstanceUID,
-                                         const Uint16 rspStatusCode);
-
-  // -- N-EVENT-REPORT --
-
-  /** Receive N-EVENT-REPORT request on the currently opened association and send a
-   *  corresponding response. Calls checkEVENTREPORTRequest() in order to determine the
-   *  DIMSE status code to be used for the N-EVENT-REPORT response.
-   *  @param reqMessage  [in]  The N-EVENT-REPORT request message that was received
-   *  @param presID      [in]  The presentation context to be used. By default, the
-   *                           presentation context of the request is used.
-   *  @param reqDataset  [out] Pointer to the dataset received
-   *  @param eventTypeID [out] Event Type ID from the command set received
-   *  @return status, EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition handleEVENTREPORTRequest(T_DIMSE_N_EventReportRQ &reqMessage,
-                                               const T_ASC_PresentationContextID presID,
-                                               DcmDataset *&reqDataset,
-                                               Uint16 &eventTypeID);
-
-  /** Send N-EVENT-REPORT request on the current association and receive a corresponding
-   *  response.
-   *  @param presID         [in]  The ID of the presentation context to be used for sending
-   *                              the request message. Should not be 0.
-   *  @param sopInstanceUID [in]  The requested SOP Instance UID
-   *  @param messageID      [in]  The request message ID
-   *  @param eventTypeID    [in]  The event type ID to be used
-   *  @param reqDataset     [in]  The request dataset to be sent
-   *  @param rspStatusCode  [out] The response status code received. 0 means success,
-   *                              others can be found in the DICOM standard.
-   *  @return EC_Normal if request could be issued and response was received successfully,
-   *          an error code otherwise
-   */
-  virtual OFCondition sendEVENTREPORTRequest(const T_ASC_PresentationContextID presID,
-                                             const OFString &sopInstanceUID,
-                                             const Uint16 messageID,
-                                             const Uint16 eventTypeID,
-                                             DcmDataset *reqDataset,
-                                             Uint16 &rspStatusCode);
-
-  /** Check given N-EVENT-REPORT request and dataset for validity. This method is called by
-   *  handleEVENTREPORTRequest() before sending the response in order to determine the
-   *  DIMSE status code to be used for the response message.
-   *  @param reqMessage [in] The N-EVENT-REPORT request message data structure
-   *  @param reqDataset [in] The N-EVENT-REPORT request dataset received. Might be NULL.
-   *  @return DIMSE status code to be used for the N-EVENT-REPORT response.
-   *          Always returns STATUS_Success (0). Derived classes should, therefore,
-   *          overwrite this method and return a more appropriate value based on the
-   *          result of the checks performed.
-   */
-  virtual Uint16 checkEVENTREPORTRequest(T_DIMSE_N_EventReportRQ &reqMessage,
-                                         DcmDataset *reqDataset);
-
-  /* ********************************************************************* */
-  /*  Further functions and member variables                               */
-  /* ********************************************************************* */
-
-  /** Helper function to return presentation context information by given
-   *  presentation context ID.
-   *  @param head The presentation context list
-   *  @param presentationContextID The presentation context ID
-   *  @return The presentation context information
-   */
-  static DUL_PRESENTATIONCONTEXT* findPresentationContextID(LST_HEAD *head,
-                                                            T_ASC_PresentationContextID presentationContextID);
-
-  /** Helper function to return presentation context information by given
-   *  presentation context ID.
-   *  @param assoc The association to search
-   *  @param presID The presentation context ID
-   *  @param presInfo The result presentation context information, if found
-   *  @return OFTrue if presentation context with ID could be found, OFFalse
-   *          otherwise
-   */
-  static OFBool getPresentationContextInfo(const T_ASC_Association *assoc,
-                                           const Uint8 presID,
-                                           DcmPresentationContextInfo &presInfo);
-
-  /** This function takes care of receiving, negotiating and accepting/refusing an
-   *  association request. Additionally, if negotiation was successful, it handles any
-   *  incoming DIMSE commands by calling handleAssociation(). An error is only returned, if
-   *  something goes wrong. Therefore, refusing an association because of wrong application
-   *  context name or no common presentation contexts with the SCU does NOT lead to an error.
-   *  @param network [in] Contains network parameters
-   *  @return EC_Normal, if everything went fine, DUL_NOASSOCIATIONREQUEST if a timeout
-   *          occurs in non-blocking mode, DIMSE_ILLEGALASSOCIATION or ASC_NULLKEY if
-   *          severe internal errors occured (should not happen)
-   */
-  virtual OFCondition waitForAssociationRQ(T_ASC_Network *network);
-
-  /** Actually process association request.
-   *  @return EC_Normal if association could be processed, ASC_NULLKEY otherwise
-   *          (only if internal association structure is invalid, should never happen)
-   */
-  virtual OFCondition processAssociationRQ();
-
- /** This function checks all presentation contexts proposed by the SCU whether they are
-  *  supported or not. It is not an error if no common presentation context could be
-  *  identified with the SCU; only issues like problems in memory management etc. are
-  *  reported as an error. This function does not send a response message to the SCU. This
-  *  is done in other functions.
-  *  @return EC_Normal if negotiation was successfully done, an error code otherwise
-  */
-  virtual OFCondition negotiateAssociation();
-
-  /** This function takes care of refusing an association request
-   *  @param reason [in] The reason why the association request will be refused and that
-   *                     will be reported to the SCU.
-   */
-  virtual void refuseAssociation(const DcmRefuseReasonType reason);
-
-  /** This function takes care of handling the other DICOM application's request. After
-   *  having accomplished all necessary steps, the association will be dropped and destroyed.
-   */
-  virtual void handleAssociation();
-
-  /** Send a DIMSE command and possibly also a dataset from a data object via network to
-   *  another DICOM application
-   *  @param presID          [in]  Presentation context ID to be used for message
-   *  @param message         [in]  Structure that represents a certain DIMSE command which
-   *                               shall be sent
-   *  @param dataObject      [in]  The instance data which shall be sent to the other DICOM
-   *                               application; NULL, if there is none
-   *  @param statusDetail    [in]  The status detail of the response (if desired).
-   *  @param commandSet      [out] If this parameter is not NULL it will return a copy of the
-   *                               DIMSE command which is sent to the other DICOM application
-   *  @return Returns EC_Normal if sending request was successful, an error code otherwise
-   */
-  OFCondition sendDIMSEMessage(const T_ASC_PresentationContextID presID,
-                               T_DIMSE_Message *message,
-                               DcmDataset *dataObject,
-                               DcmDataset *statusDetail = NULL,
-                               DcmDataset **commandSet = NULL);
-
-  /** Receive DIMSE command (excluding dataset!) over the currently open association
-   *  @param presID       [out] Contains in the end the ID of the presentation context
-   *                            which was specified in the DIMSE command received
-   *  @param message      [out] The message received
-   *  @param statusDetail [out] If a non-NULL value is passed this variable will in the end
-   *                            contain detailed information with regard to the status
-   *                            information which is captured in the status element
-   *                            (0000,0900). Note that the value for element (0000,0900) is
-   *                            not contained in this return value but in internal message.
-   *                            For details on the structure of this object, see DICOM
-   *                            standard part 7, annex C).
-   *  @param commandSet   [out] If this parameter is not NULL, it will return a copy of the
-   *                            DIMSE command which was received from the other DICOM
-   *                            application. The caller is responsible to de-allocate the
-   *                            returned object!
-   *  @param timeout      [in]  If this parameter is not 0, it specifies the timeout (in
-   *                            seconds) to be used for receiving the DIMSE command.
-   *                            Otherwise, the default timeout value is used (see
-   *                            setDIMSETimeout()).
-   *  @return EC_Normal if command could be received successfully, an error code otherwise
-   */
-  OFCondition receiveDIMSECommand(T_ASC_PresentationContextID *presID,
-                                  T_DIMSE_Message *message,
-                                  DcmDataset **statusDetail,
-                                  DcmDataset **commandSet = NULL,
-                                  const Uint32 timeout = 0);
-
-  /** Receive one dataset (of instance data) via network from another DICOM application
-   *  @param presID     [out]   Contains in the end the ID of the presentation context
-   *                            which was used in the PDVs that were received on the
-   *                            network. If the PDVs show different presentation context
-   *                            IDs, this function will return an error.
-   *  @param dataObject [inout] Contains in the end the information that was received
-   *                            over the network. If this parameter points to NULL, a new
-   *                            dataset will be created by the underlying routines, which
-   *                            has to be deleted by the caller.
-   *  @return EC_Normal if dataset could be received successfully, an error code otherwise
-   */
-  OFCondition receiveDIMSEDataset(T_ASC_PresentationContextID *presID,
-                                  DcmDataset **dataObject);
-
-  /** Receive one C-STORE request dataset via network from another DICOM application and
-   *  store it directly to file (i.e.\ exactly as received without any conversions)
-   *  @param presID      [inout] Initially, the presentation context the C-STORE request was
-   *                             received on. Contains in the end the ID of the presentation
-   *                             context which was used in the PDVs that were received on the
-   *                             network. If the PDVs show different presentation context
-   *                             IDs, this function will return an error.
-   *  @param reqMessage  [in]    The C-STORE request message that was received
-   *  @param filename    [in]    Name of the file that is created to store the received dataset
-   *  @return EC_Normal if dataset could be received successfully, an error code otherwise
-   */
-  OFCondition receiveSTORERequestDataset(T_ASC_PresentationContextID *presID,
-                                         T_DIMSE_C_StoreRQ &reqMessage,
-                                         const OFString &filename);
-
-  /** Add given element to existing status detail object or create new one.
-   *  @param statusDetail  The status detail to add the element to. Status detail
-   *           is information additional to the DIMSE status code which can be
-   *           provided for some DIMSE messages. If NULL is provided,
-   *           a new status detail object is created and returned. All status
-   *           detail attributes need to have the VR AT or LO which is also
-   *           checked by the underlying routine.
-   *  @param elem The element to be copied into the status detail.
-   *  @return OFTrue if status detail was successfully added,
-   *          OFFalse otherwise.
-   */
-  static OFBool addStatusDetail(DcmDataset **statusDetail,
-                                const DcmElement *elem);
-
-  /* Callback functions (static) */
-
-  /** Callback function used for sending DIMSE messages.
-   *  @param callbackContext [in] The desired user callback data
-   *  @param byteCount       [in] Progress bytes count
-   */
-  static void callbackSENDProgress(void *callbackContext,
-                                   unsigned long byteCount);
-
-  /** Callback function used for receiving DIMSE messages.
-   *  @param callbackContext [in] The desired user callback data
-   *  @param byteCount       [in] Progress bytes count
-   */
-  static void callbackRECEIVEProgress(void *callbackContext,
-                                      unsigned long byteCount);
+                                         const OFString& sopClassUID,
+                                         DcmDataset* rspDataset,
+                                         const Uint16 rspStatusCode,
+                                         DcmDataset* statusDetail = NULL,
+                                         const Uint16 numRemain   = 0,
+                                         const Uint16 numComplete = 0,
+                                         const Uint16 numFail     = 0,
+                                         const Uint16 numWarn     = 0);
+
+    // -- N-ACTION --
+
+    /** Receive N-ACTION request on the currently opened association.
+     *  @param reqMessage   [in]  The N-ACTION request message that was received
+     *  @param presID       [in]  The presentation context to be used. By default, the
+     *                            presentation context of the request is used.
+     *  @param reqDataset   [out] Pointer to the dataset received
+     *  @param actionTypeID [out] Action Type ID from the command set received
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition receiveACTIONRequest(T_DIMSE_N_ActionRQ& reqMessage,
+                                             const T_ASC_PresentationContextID presID,
+                                             DcmDataset*& reqDataset,
+                                             Uint16& actionTypeID);
+
+    /** Receive N-ACTION request on the currently opened association. This
+     *  function is deprecated and will be removed in the future. For now it calls
+     *  receiveACTIONRequest() which should be used instead.
+     *  @param reqMessage   [in]  The N-ACTION request message that was received
+     *  @param presID       [in]  The presentation context to be used. By default, the
+     *                            presentation context of the request is used.
+     *  @param reqDataset   [out] Pointer to the dataset received
+     *  @param actionTypeID [out] Action Type ID from the command set received
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition handleACTIONRequest(T_DIMSE_N_ActionRQ& reqMessage,
+                                            const T_ASC_PresentationContextID presID,
+                                            DcmDataset*& reqDataset,
+                                            Uint16& actionTypeID)
+    {
+        DCMNET_WARN("handleACTIONRequest() is deprecated, use receiveACTIONRequest() instead");
+        return receiveACTIONRequest(reqMessage, presID, reqDataset, actionTypeID);
+    }
+
+    /** Respond to the N-ACTION request
+     *  @param presID         [in] The presentation context ID to respond to
+     *  @param messageID      [in] The message ID being responded to
+     *  @param sopClassUID    [in] The affected SOP class UID
+     *  @param sopInstanceUID [in] The affected SOP instance UID
+     *  @param rspStatusCode  [in] The response status code. 0 means success,
+     *                             others can found in the DICOM standard.
+     *  @return EC_Normal, if responding was successful, an error code otherwise
+     */
+    virtual OFCondition sendACTIONResponse(const T_ASC_PresentationContextID presID,
+                                           const Uint16 messageID,
+                                           const OFString& sopClassUID,
+                                           const OFString& sopInstanceUID,
+                                           const Uint16 rspStatusCode);
+
+    // -- N-EVENT-REPORT --
+
+    /** Receive N-EVENT-REPORT request on the currently opened association and send a
+     *  corresponding response. Calls checkEVENTREPORTRequest() in order to determine the
+     *  DIMSE status code to be used for the N-EVENT-REPORT response.
+     *  @param reqMessage  [in]  The N-EVENT-REPORT request message that was received
+     *  @param presID      [in]  The presentation context to be used. By default, the
+     *                           presentation context of the request is used.
+     *  @param reqDataset  [out] Pointer to the dataset received
+     *  @param eventTypeID [out] Event Type ID from the command set received
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition handleEVENTREPORTRequest(T_DIMSE_N_EventReportRQ& reqMessage,
+                                                 const T_ASC_PresentationContextID presID,
+                                                 DcmDataset*& reqDataset,
+                                                 Uint16& eventTypeID);
+
+    /** Send N-EVENT-REPORT request on the current association and receive a corresponding
+     *  response.
+     *  @param presID         [in]  The ID of the presentation context to be used for sending
+     *                              the request message. Should not be 0.
+     *  @param sopInstanceUID [in]  The requested SOP Instance UID
+     *  @param messageID      [in]  The request message ID
+     *  @param eventTypeID    [in]  The event type ID to be used
+     *  @param reqDataset     [in]  The request dataset to be sent
+     *  @param rspStatusCode  [out] The response status code received. 0 means success,
+     *                              others can be found in the DICOM standard.
+     *  @return EC_Normal if request could be issued and response was received successfully,
+     *          an error code otherwise
+     */
+    virtual OFCondition sendEVENTREPORTRequest(const T_ASC_PresentationContextID presID,
+                                               const OFString& sopInstanceUID,
+                                               const Uint16 messageID,
+                                               const Uint16 eventTypeID,
+                                               DcmDataset* reqDataset,
+                                               Uint16& rspStatusCode);
+
+    /** Check given N-EVENT-REPORT request and dataset for validity. This method is called by
+     *  handleEVENTREPORTRequest() before sending the response in order to determine the
+     *  DIMSE status code to be used for the response message.
+     *  @param reqMessage [in] The N-EVENT-REPORT request message data structure
+     *  @param reqDataset [in] The N-EVENT-REPORT request dataset received. Might be NULL.
+     *  @return DIMSE status code to be used for the N-EVENT-REPORT response.
+     *          Always returns STATUS_Success (0). Derived classes should, therefore,
+     *          overwrite this method and return a more appropriate value based on the
+     *          result of the checks performed.
+     */
+    virtual Uint16 checkEVENTREPORTRequest(T_DIMSE_N_EventReportRQ& reqMessage, DcmDataset* reqDataset);
+
+    /* ********************************************************************* */
+    /*  Further functions and member variables                               */
+    /* ********************************************************************* */
+
+    /** Helper function to return presentation context information by given
+     *  presentation context ID.
+     *  @param head The presentation context list
+     *  @param presentationContextID The presentation context ID
+     *  @return The presentation context information
+     */
+    static DUL_PRESENTATIONCONTEXT* findPresentationContextID(LST_HEAD* head,
+                                                              T_ASC_PresentationContextID presentationContextID);
+
+    /** Helper function to return presentation context information by given
+     *  presentation context ID.
+     *  @param assoc The association to search
+     *  @param presID The presentation context ID
+     *  @param presInfo The result presentation context information, if found
+     *  @return OFTrue if presentation context with ID could be found, OFFalse
+     *          otherwise
+     */
+    static OFBool getPresentationContextInfo(const T_ASC_Association* assoc,
+                                             const Uint8 presID,
+                                             DcmPresentationContextInfo& presInfo);
+
+    /** This function takes care of receiving, negotiating and accepting/refusing an
+     *  association request. Additionally, if negotiation was successful, it handles any
+     *  incoming DIMSE commands by calling handleAssociation(). An error is only returned, if
+     *  something goes wrong. Therefore, refusing an association because of wrong application
+     *  context name or no common presentation contexts with the SCU does NOT lead to an error.
+     *  @param network [in] Contains network parameters
+     *  @return EC_Normal, if everything went fine, DUL_NOASSOCIATIONREQUEST if a timeout
+     *          occurs in non-blocking mode, DIMSE_ILLEGALASSOCIATION or ASC_NULLKEY if
+     *          severe internal errors occurred (should not happen)
+     */
+    virtual OFCondition waitForAssociationRQ(T_ASC_Network* network);
+
+    /** Actually process association request.
+     *  @return EC_Normal if association could be processed, ASC_NULLKEY otherwise
+     *          (only if internal association structure is invalid, should never happen)
+     */
+    virtual OFCondition processAssociationRQ();
+
+    /** This function checks all presentation contexts proposed by the SCU whether they are
+     *  supported or not. It is not an error if no common presentation context could be
+     *  identified with the SCU; only issues like problems in memory management etc. are
+     *  reported as an error. This function does not send a response message to the SCU. This
+     *  is done in other functions.
+     *  @return EC_Normal if negotiation was successfully done, an error code otherwise
+     */
+    virtual OFCondition negotiateAssociation();
+
+    /** This function takes care of refusing an association request
+     *  @param reason [in] The reason why the association request will be refused and that
+     *                     will be reported to the SCU.
+     */
+    virtual void refuseAssociation(const DcmRefuseReasonType reason);
+
+    /** This function takes care of handling the other DICOM application's request. After
+     *  having accomplished all necessary steps, the association will be dropped and destroyed.
+     */
+    virtual void handleAssociation();
+
+    /** Send a DIMSE command and possibly also a dataset from a data object via network to
+     *  another DICOM application
+     *  @param presID          [in]  Presentation context ID to be used for message
+     *  @param message         [in]  Structure that represents a certain DIMSE command which
+     *                               shall be sent
+     *  @param dataObject      [in]  The instance data which shall be sent to the other DICOM
+     *                               application; NULL, if there is none
+     *  @param statusDetail    [in]  The status detail of the response (if desired).
+     *  @param commandSet      [out] If this parameter is not NULL it will return a copy of the
+     *                               DIMSE command which is sent to the other DICOM application
+     *  @return Returns EC_Normal if sending request was successful, an error code otherwise
+     */
+    OFCondition sendDIMSEMessage(const T_ASC_PresentationContextID presID,
+                                 T_DIMSE_Message* message,
+                                 DcmDataset* dataObject,
+                                 DcmDataset* statusDetail = NULL,
+                                 DcmDataset** commandSet  = NULL);
+
+    /** Receive DIMSE command (excluding dataset!) over the currently open association
+     *  @param presID       [out] Contains in the end the ID of the presentation context
+     *                            which was specified in the DIMSE command received
+     *  @param message      [out] The message received
+     *  @param statusDetail [out] If a non-NULL value is passed this variable will in the end
+     *                            contain detailed information with regard to the status
+     *                            information which is captured in the status element
+     *                            (0000,0900). Note that the value for element (0000,0900) is
+     *                            not contained in this return value but in internal message.
+     *                            For details on the structure of this object, see DICOM
+     *                            standard part 7, annex C).
+     *  @param commandSet   [out] If this parameter is not NULL, it will return a copy of the
+     *                            DIMSE command which was received from the other DICOM
+     *                            application. The caller is responsible to de-allocate the
+     *                            returned object!
+     *  @param timeout      [in]  If this parameter is not 0, it specifies the timeout (in
+     *                            seconds) to be used for receiving the DIMSE command.
+     *                            Otherwise, the default timeout value is used (see
+     *                            setDIMSETimeout()).
+     *  @return EC_Normal if command could be received successfully, an error code otherwise
+     */
+    OFCondition receiveDIMSECommand(T_ASC_PresentationContextID* presID,
+                                    T_DIMSE_Message* message,
+                                    DcmDataset** statusDetail,
+                                    DcmDataset** commandSet = NULL,
+                                    const Uint32 timeout    = 0);
+
+    /** Receive one dataset (of instance data) via network from another DICOM application
+     *  @param presID     [out]   Contains in the end the ID of the presentation context
+     *                            which was used in the PDVs that were received on the
+     *                            network. If the PDVs show different presentation context
+     *                            IDs, this function will return an error.
+     *  @param dataObject [inout] Contains in the end the information that was received
+     *                            over the network. If this parameter points to NULL, a new
+     *                            dataset will be created by the underlying routines, which
+     *                            has to be deleted by the caller.
+     *  @return EC_Normal if dataset could be received successfully, an error code otherwise
+     */
+    OFCondition receiveDIMSEDataset(T_ASC_PresentationContextID* presID, DcmDataset** dataObject);
+
+    /** Receive one C-STORE request dataset via network from another DICOM application and
+     *  store it directly to file (i.e.\ exactly as received without any conversions)
+     *  @param presID      [inout] Initially, the presentation context the C-STORE request was
+     *                             received on. Contains in the end the ID of the presentation
+     *                             context which was used in the PDVs that were received on the
+     *                             network. If the PDVs show different presentation context
+     *                             IDs, this function will return an error.
+     *  @param reqMessage  [in]    The C-STORE request message that was received
+     *  @param filename    [in]    Name of the file that is created to store the received dataset
+     *  @return EC_Normal if dataset could be received successfully, an error code otherwise
+     */
+    OFCondition receiveSTORERequestDataset(T_ASC_PresentationContextID* presID,
+                                           T_DIMSE_C_StoreRQ& reqMessage,
+                                           const OFString& filename);
+
+    /** Add given element to existing status detail object or create new one.
+     *  @param statusDetail  The status detail to add the element to. Status detail
+     *           is information additional to the DIMSE status code which can be
+     *           provided for some DIMSE messages. If NULL is provided,
+     *           a new status detail object is created and returned. All status
+     *           detail attributes need to have the VR AT or LO which is also
+     *           checked by the underlying routine.
+     *  @param elem The element to be copied into the status detail.
+     *  @return OFTrue if status detail was successfully added,
+     *          OFFalse otherwise.
+     */
+    static OFBool addStatusDetail(DcmDataset** statusDetail, const DcmElement* elem);
+
+    /* Callback functions (static) */
+
+    /** Callback function used for sending DIMSE messages.
+     *  @param callbackContext [in] The desired user callback data
+     *  @param byteCount       [in] Progress bytes count
+     */
+    static void callbackSENDProgress(void* callbackContext, unsigned long byteCount);
+
+    /** Callback function used for receiving DIMSE messages.
+     *  @param callbackContext [in] The desired user callback data
+     *  @param byteCount       [in] Progress bytes count
+     */
+    static void callbackRECEIVEProgress(void* callbackContext, unsigned long byteCount);
 
 private:
-
-  /// Current association run by this SCP
-  T_ASC_Association *m_assoc;
-
-  /// SCP configuration. The configuration is a shared object since in some scenarios one
-  /// might like to share a single configuration instance with multiple SCPs without copying
-  /// it, e.g. in the context of the DcmSCPPool class.
-  DcmSharedSCPConfig m_cfg;
-
-  /** Drops association and clears internal structures to free memory
-   */
-  void dropAndDestroyAssociation();
-
-  /** Private undefined copy constructor. Shall never be called.
-   *  @param src Source object
-   */
-  DcmSCP(const DcmSCP &src);
-
-  /** Private undefined assignment operator. Shall never be called.
-   *  @param src Source object
-   *  @return Reference to this
-   */
-  DcmSCP &operator=(const DcmSCP &src);
+    /// Network instance run by this SCP
+    T_ASC_Network* m_network;
+
+    /// Current association run by this SCP
+    T_ASC_Association* m_assoc;
+
+    /// SCP configuration. The configuration is a shared object since in some scenarios one
+    /// might like to share a single configuration instance with multiple SCPs without copying
+    /// it, e.g. in the context of the DcmSCPPool class.
+    DcmSharedSCPConfig m_cfg;
+
+    /** Drops association and clears internal structures to free memory
+     */
+    void dropAndDestroyAssociation();
+
+    /** Private undefined copy constructor. Shall never be called.
+     *  @param src Source object
+     */
+    DcmSCP(const DcmSCP& src);
+
+    /** Private undefined assignment operator. Shall never be called.
+     *  @param src Source object
+     *  @return Reference to this
+     */
+    DcmSCP& operator=(const DcmSCP& src);
 };
 
 #endif // SCP_H
index bce3c364f646173ec603f83fedcec88fa7d1ca1b..9d23a078d41c4a6ce1ce8fb1838155f691ee74df 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2012-2017, OFFIS e.V.
+ *  Copyright (C) 2012-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -28,6 +28,8 @@
 #include "dcmtk/dcmnet/dimse.h"
 #include "dcmtk/ofstd/ofmem.h"      /* For OFshared_ptr */
 
+class DcmTransportLayer;
+
 /** Class that encapsulates an SCP configuration that is needed in order to
  *  configure the service negotiation behavior (presentation contexts, AE
  *  title, listening port, etc) as well as some runtime configuration like
@@ -296,6 +298,23 @@ public:
    */
   OFBool getProgressNotificationMode() const;
 
+  /** Returns true if an external transport layer (e.g. TLS) is enabled,
+   *  false if the default, transparent layer is used.
+   *  @return true if an external transport layer is enabled
+   */
+  OFBool transportLayerEnabled() const;
+
+  /** Returns pointer to the transport layer object in use
+   *  @return pointer to the transport layer object in use, may be NULL.
+   */
+  DcmTransportLayer * getTransportLayer() const;
+
+  /** set an explicit transport layer (e.g. for TLS communication) to use
+   *  @param tlayer [in] The transport layer object.
+   *                     This function does not take ownership of tlayer.
+   */
+  void setTransportLayer(DcmTransportLayer *tlayer);
+
   /** Dump presentation contexts to given output stream, useful for debugging.
    *  @param out [out] The output stream
    *  @param profileName [in] The profile to dump. If empty (default), the currently
@@ -393,6 +412,10 @@ protected:
 
   /// Progress notification mode (default: OFTrue)
   OFBool m_progressNotificationMode;
+
+  /// The transport layer in use for communication (e.g. for TLS). 
+  /// Default is NULL for the normal TCP layer.
+  DcmTransportLayer *m_tLayer; /// Doesn't have ownership
 };
 
 /** Enables sharing configurations by multiple DcmSCPs.
index 815f2545766466348ec312d97c11b4db66be03ff..68924dd33606648b3cd9daf4efdde2447b0b898c 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2008-2017, OFFIS e.V.
+ *  Copyright (C) 2008-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #ifndef SCU_H
 #define SCU_H
 
-#include "dcmtk/config/osconfig.h"  /* make sure OS specific configuration is included first */
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 
-#include "dcmtk/dcmdata/dctk.h"     /* covers most common dcmdata classes */
+#include "dcmtk/dcmdata/dctk.h"    /* covers most common dcmdata classes */
+#include "dcmtk/dcmnet/dcasccff.h" /* for reading a association config file */
+#include "dcmtk/dcmnet/dcasccfg.h" /* for holding association config file infos */
 #include "dcmtk/dcmnet/dcompat.h"
-#include "dcmtk/dcmnet/dimse.h"     /* DIMSE network layer */
-#include "dcmtk/dcmnet/dcasccff.h"  /* for reading a association config file */
-#include "dcmtk/dcmnet/dcasccfg.h"  /* for holding association config file infos */
+#include "dcmtk/dcmnet/dimse.h" /* DIMSE network layer */
 #include "dcmtk/ofstd/oflist.h"
 
-
 // include this file in doxygen documentation
 
 /** @file scu.h
  *  @brief general Service Class User (SCU) class
  */
 
-
 /** Different types of closing an association
  */
 enum DcmCloseAssociationType
 {
-  /// Release the current association
-  DCMSCU_RELEASE_ASSOCIATION,
-  /// Abort the current association
-  DCMSCU_ABORT_ASSOCIATION,
-  /// Peer requested release (Aborting)
-  DCMSCU_PEER_REQUESTED_RELEASE,
-  /// Peer aborted the association
-  DCMSCU_PEER_ABORTED_ASSOCIATION
+    /// Release the current association
+    DCMSCU_RELEASE_ASSOCIATION,
+    /// Abort the current association
+    DCMSCU_ABORT_ASSOCIATION,
+    /// Peer requested release (Aborting)
+    DCMSCU_PEER_REQUESTED_RELEASE,
+    /// Peer aborted the association
+    DCMSCU_PEER_ABORTED_ASSOCIATION
 };
 
 /** Storage mode used for DICOM objects received via C-STORE
  */
 enum DcmStorageMode
 {
-  /// Ignore any objects received via C-STORE
-  DCMSCU_STORAGE_IGNORE,
-  /// Try to store the objects to disk
-  DCMSCU_STORAGE_DISK,
-  /// Try to store to disk in bit-preserving mode. This is especially useful
-  /// for huge files that cannot fully be received in memory since the data
-  /// is directly streamed to disk. Originally, this was introduced for DICOM
-  /// signatures which can be kept valid this way.
-  DCMSCU_STORAGE_BIT_PRESERVING
+    /// Ignore any objects received via C-STORE
+    DCMSCU_STORAGE_IGNORE,
+    /// Try to store the objects to disk
+    DCMSCU_STORAGE_DISK,
+    /// Try to store to disk in bit-preserving mode. This is especially useful
+    /// for huge files that cannot fully be received in memory since the data
+    /// is directly streamed to disk. Originally, this was introduced for DICOM
+    /// signatures which can be kept valid this way.
+    DCMSCU_STORAGE_BIT_PRESERVING
 };
 
-
 /** Base class for C-FIND, C-MOVE and C-GET responses
  */
 class DCMTK_DCMNET_EXPORT QRResponse
 {
-  public:
-
-  /** Standard constructor.
-   */
-  QRResponse() :
-    m_messageIDRespondedTo(0),
-    m_affectedSOPClassUID(),
-    m_dataset(NULL),
-    m_status(0),
-    m_statusDetail(NULL) {}
-
-  /** Destructor, cleans up internal memory (dataset if present).
-   */
-  virtual ~QRResponse() { delete m_dataset; delete m_statusDetail; }
-
-  /// The message ID responded to (mandatory response field,
-  /// equals message ID from request)
-  Uint16 m_messageIDRespondedTo;
-
-  /// Optional response field according to part 7 of the standard.
-  /// If present, equals SOP Class UID from request.
-  OFString m_affectedSOPClassUID;
-
-  /// Conditional response field (NULL if absent). From the standard (2009,
-  /// part 4, C.4.2.1.4.2), for C-MOVE: In Q/R if no C-STORE sub-operation
-  /// failed, Failed SOP Instance UID List (0008,0058) is absent and
-  /// therefore no Data Set shall be sent in the C-MOVE response. Further
-  /// rules: Statuses of Canceled, Failure, Refused, or Warning shall
-  /// contain the Failed SOP Instance UID List Attribute; status of
-  /// Pending shall not.
-  DcmDataset *m_dataset;
-
-  /// The returned DIMSE status (mandatory Response Field)
-  Uint16 m_status;
-
-  /// Status detail (NULL if absent). For some DIMSE return status codes,
-  /// an additional dataset is sent which gives further information (i.e.
-  /// in case of warnings or errors).
-  DcmDataset *m_statusDetail;
+public:
+    /** Standard constructor.
+     */
+    QRResponse()
+        : m_messageIDRespondedTo(0)
+        , m_affectedSOPClassUID()
+        , m_dataset(NULL)
+        , m_status(0)
+        , m_statusDetail(NULL)
+    {
+    }
 
-private:
+    /** Destructor, cleans up internal memory (dataset if present).
+     */
+    virtual ~QRResponse()
+    {
+        delete m_dataset;
+        delete m_statusDetail;
+    }
 
-  /** Private undefined copy constructor.
-   * @param other The find response to copy from
-   */
-  QRResponse(const QRResponse &other);
+    /// The message ID responded to (mandatory response field,
+    /// equals message ID from request)
+    Uint16 m_messageIDRespondedTo;
 
-  /** Private undefined assignment operator.
-   *  @param other The find response that should be assigned from
-   *  @return Reference to this
-   */
-  QRResponse &operator=(const QRResponse &other);
-};
+    /// Optional response field according to part 7 of the standard.
+    /// If present, equals SOP Class UID from request.
+    OFString m_affectedSOPClassUID;
+
+    /// Conditional response field (NULL if absent). From the standard (2009,
+    /// part 4, C.4.2.1.4.2), for C-MOVE: In Q/R if no C-STORE sub-operation
+    /// failed, Failed SOP Instance UID List (0008,0058) is absent and
+    /// therefore no Data Set shall be sent in the C-MOVE response. Further
+    /// rules: Statuses of Canceled, Failure, Refused, or Warning shall
+    /// contain the Failed SOP Instance UID List Attribute; status of
+    /// Pending shall not.
+    DcmDataset* m_dataset;
+
+    /// The returned DIMSE status (mandatory Response Field)
+    Uint16 m_status;
+
+    /// Status detail (NULL if absent). For some DIMSE return status codes,
+    /// an additional dataset is sent which gives further information (i.e.
+    /// in case of warnings or errors).
+    DcmDataset* m_statusDetail;
+
+private:
+    /** Private undefined copy constructor.
+     * @param other The find response to copy from
+     */
+    QRResponse(const QRResponse& other);
 
+    /** Private undefined assignment operator.
+     *  @param other The find response that should be assigned from
+     *  @return Reference to this
+     */
+    QRResponse& operator=(const QRResponse& other);
+};
 
 /// Base class representing for single C-GET or C-MOVE response
 class DCMTK_DCMNET_EXPORT RetrieveResponse : public QRResponse
 {
 public:
-  /** Standard constructor
-   */
-  RetrieveResponse() :
-        m_numberOfRemainingSubops(0),
-        m_numberOfCompletedSubops(0),
-        m_numberOfFailedSubops(0),
-        m_numberOfWarningSubops(0) {}
-
-  /** Destructor, cleans up internal memory
-   */
-  virtual ~RetrieveResponse() {}
-
-  /** Prints response to INFO log level.
-   */
-  void print();
-
-  /// Number of remaining sub operations (in Q/R: C-STORE calls).
-  /// For Q/R MOVE and GET, for status of pending this field shall be filled.
-  /// For others, the field may be filled.
-  Uint16 m_numberOfRemainingSubops;
-
-  /// Number of successfully completed sub operations (in Q/R: C-STORE calls).
-  /// For Q/R MOVE and GET, for status of pending this field shall be filled.
-  /// For others, the field may be filled.
-  Uint16 m_numberOfCompletedSubops;
-
-  /// Number of failed sub operations (in Q/R: C-STORE calls).
-  /// For Q/R MOVE and GET, for status of pending this field shall be filled.
-  /// For others, the field may be filled.
-  Uint16 m_numberOfFailedSubops;
-
-  /// Number generated warnings generated by sub operations (in Q/R: C-STORE calls).
-  /// For Q/R MOVE and GET, for status of pending this field shall be filled.
-  /// For others, the field may be filled.
-  Uint16 m_numberOfWarningSubops;
+    /** Standard constructor
+     */
+    RetrieveResponse()
+        : m_numberOfRemainingSubops(0)
+        , m_numberOfCompletedSubops(0)
+        , m_numberOfFailedSubops(0)
+        , m_numberOfWarningSubops(0)
+    {
+    }
 
-private:
+    /** Destructor, cleans up internal memory
+     */
+    virtual ~RetrieveResponse()
+    {
+    }
 
-  /** Private undefined copy constructor
-   *  @param other Response to copy from
-   */
-  RetrieveResponse(const RetrieveResponse &other);
+    /** Prints response to INFO log level.
+     */
+    void print();
 
-  /** Private undefined assignment operator
-   *  @param other Response that should be assigned from
-   *  @return Reference to this
-   */
-  RetrieveResponse &operator=(const RetrieveResponse &other);
-};
+    /// Number of remaining sub operations (in Q/R: C-STORE calls).
+    /// For Q/R MOVE and GET, for status of pending this field shall be filled.
+    /// For others, the field may be filled.
+    Uint16 m_numberOfRemainingSubops;
+
+    /// Number of successfully completed sub operations (in Q/R: C-STORE calls).
+    /// For Q/R MOVE and GET, for status of pending this field shall be filled.
+    /// For others, the field may be filled.
+    Uint16 m_numberOfCompletedSubops;
 
+    /// Number of failed sub operations (in Q/R: C-STORE calls).
+    /// For Q/R MOVE and GET, for status of pending this field shall be filled.
+    /// For others, the field may be filled.
+    Uint16 m_numberOfFailedSubops;
+
+    /// Number generated warnings generated by sub operations (in Q/R: C-STORE calls).
+    /// For Q/R MOVE and GET, for status of pending this field shall be filled.
+    /// For others, the field may be filled.
+    Uint16 m_numberOfWarningSubops;
+
+private:
+    /** Private undefined copy constructor
+     *  @param other Response to copy from
+     */
+    RetrieveResponse(const RetrieveResponse& other);
+
+    /** Private undefined assignment operator
+     *  @param other Response that should be assigned from
+     *  @return Reference to this
+     */
+    RetrieveResponse& operator=(const RetrieveResponse& other);
+};
 
 /** Base class for implementing DICOM Service Class User functionality. The class offers
  *  support for negotiating associations and sending and receiving arbitrary DIMSE messages
@@ -193,885 +195,884 @@ class DCMTK_DCMNET_EXPORT DcmSCU
 {
 
 public:
+    /** Constructor, just initializes internal class members
+     */
+    DcmSCU();
 
-  /** Constructor, just initializes internal class members
-   */
-  DcmSCU();
-
-  /** Virtual destructor
-   */
-  virtual ~DcmSCU();
-
-  /** Add presentation context to be used for association negotiation
-   *  @param abstractSyntax [in] Abstract syntax name in UID format
-   *  @param xferSyntaxes   [in] List of transfer syntaxes to be added for the given abstract
-   *                             syntax
-   *  @param role           [in] The role to be negotiated
-   *  @return EC_Normal if adding was successful, otherwise error code
-   */
-  OFCondition addPresentationContext(const OFString &abstractSyntax,
-                                     const OFList<OFString> &xferSyntaxes,
-                                     const T_ASC_SC_ROLE role = ASC_SC_ROLE_DEFAULT);
-
-  /** Initialize network, i.e.\ prepare for association negotiation. If the SCU is already
-   *  connected, the call will not be successful and the old connection keeps open.
-   *  @return EC_Normal if initialization was successful, otherwise error code.
-   *          NET_EC_AlreadyConnected if SCU is already connected.
-   */
-  virtual OFCondition initNetwork();
-
-  /** Negotiate association by using presentation contexts and parameters as defined by
-   *  earlier function calls. If negotiation fails, there is no need to close the association
-   *  or to do anything else with this class.
-   *  @return EC_Normal if negotiation was successful, otherwise error code.
-   *          NET_EC_AlreadyConnected if SCU is already connected.
-   */
-  virtual OFCondition negotiateAssociation();
-
-  /** After negotiation association, this call returns the first usable presentation context
-   *  given the desired abstract syntax and transfer syntax
-   *  @param abstractSyntax [in] The abstract syntax (UID) to look for
-   *  @param transferSyntax [in] The transfer syntax (UID) to look for. If empty, the transfer
-   *                             syntax is not checked.
-   *  @param requestorRole  [in] The role to look for (denoting the role the association
-   *                             requestor plays)
-   *  @return Adequate Presentation context ID that can be used. 0 if none found.
-   */
-  T_ASC_PresentationContextID findPresentationContextID(const OFString &abstractSyntax,
-                                                        const OFString &transferSyntax,
-                                                        const T_ASC_SC_ROLE requestorRole = ASC_SC_ROLE_DEFAULT);
-
-  /** After a successful association negotiation, this function is called to return the
-   *  presentation context ID that best matches the desired abstract syntax and transfer
-   *  syntax (TS). The function tries to do the following:
-   *  - If possible finds a presentation context with matching TS
-   *  - Else then tries to find an explicit VR uncompressed TS presentation context
-   *  - Else then tries to find an implicit VR uncompressed TS presentation context
-   *  - Else finally accepts each matching presentation ctx independent of TS.
-   *  @warning This method does not support filtering for a specific role, yet.
-   *  @param abstractSyntax [in] The abstract syntax (UID) to look for
-   *  @param transferSyntax [in] The transfer syntax (UID) to look for. If empty, the transfer
-   *                             syntax is not checked.
-   *  @return Adequate Presentation context ID that can be used. 0 if no appropriate
-   *  presentation context could be found at all.
-   */
-   T_ASC_PresentationContextID findAnyPresentationContextID(const OFString &abstractSyntax,
-                                                            const OFString &transferSyntax);
-
-  /** This function sends a C-ECHO command via network to another DICOM application
-   *  @param presID [in] Presentation context ID to use. A value of 0 lets SCP class tries
-   *                     to choose one on its own.
-   *  @return EC_Normal if echo was successful, an error code otherwise
-   *
-   */
-  virtual OFCondition sendECHORequest(const T_ASC_PresentationContextID presID);
-
-  /** This function sends a C-STORE request on the currently opened association and receives
-   *  the corresponding response then. If required and supported, the dataset of the SOP
-   *  instance can be converted automatically to the network transfer syntax that was
-   *  negotiated (and is specified by the parameter 'presID'). However, this feature is
-   *  disabled by default. See setDatasetConversionMode() on how to enable it.
-   *  @param presID        [in]  Contains in the end the ID of the presentation context which
-   *                             was specified in the DIMSE command. If 0 is given, the
-   *                             function tries to find an appropriate presentation context
-   *                             itself (based on SOP class and original transfer syntax of
-   *                             the 'dicomFile' or 'dataset').
-   *  @param dicomFile     [in]  The filename of the DICOM file to be sent. Alternatively, a
-   *                             dataset can be given in the next parameter. If both are given
-   *                             the dataset from the file name is used.
-   *  @param dataset       [in]  The dataset to be sent. Alternatively, a filename can be
-   *                             specified in the previous parameter. If both are given the
-   *                             dataset from the filename is used.
-   *  @param rspStatusCode [out] The response status code received. 0 means success, others
-   *                             can be found in the DICOM standard.
-   *  @param moveOriginatorAETitle [in] If this C-STORE is started due to a C-MOVE request,
-   *                               this parameter informs the C-STORE SCP about the C-MOVE
-   *                               client's AE title.
-   *  @param moveOriginatorMsgID   [in] If this C-STORE is started due to a C-MOVE request,
-   *                               this parameter informs the C-STORE SCP about the C-MOVE
-   *                               message ID.
-   *  @return EC_Normal if request could be issued and response was received successfully,
-   *          error code otherwise. That means that if the receiver sends a response denoting
-   *          failure of the storage request, EC_Normal will be returned.
-   */
-  virtual OFCondition sendSTORERequest(const T_ASC_PresentationContextID presID,
-                                       const OFFilename &dicomFile,
-                                       DcmDataset *dataset,
-                                       Uint16 &rspStatusCode,
-                                       const OFString &moveOriginatorAETitle = "",
-                                       const Uint16 moveOriginatorMsgID = 0);
-
-  /** Sends a C-MOVE Request on given presentation context and receives list of responses.
-   *  The function receives the first response and then calls the function handleMOVEResponse()
-   *  which gets the relevant presentation context together with the response dataset and
-   *  status information. Then it waits again for the next response, if there are more to
-   *  come (i.e. response status is PENDING). In the end, after receiving all responses, the
-   *  full list of responses is returned to the caller. If he is not interested, he just sets
-   *  responses=NULL when calling the function.
-   *  This function can be overwritten by actual SCU implementations but just should work fine
-   *  for most people.
-   *  @param presID                 [in]  The presentation context ID that should be used.
-   *                                      Must be an odd number.
-   *  @param moveDestinationAETitle [in]  The move destination's AE title, i.e.\ the one that
-   *                                      is used for connection to the storage server.
-   *  @param dataset                [in]  The dataset containing the information about the
-   *                                      object(s) to be retrieved.
-   *  @param responses              [out] The incoming C-MOVE responses for this request.
-   *                                      The caller is responsible for providing a non-NULL
-   *                                      pointer for this case. After receiving the results,
-   *                                      the caller is responsible for freeing the memory of
-   *                                      this variable. If NULL is specified, the responses
-   *                                      will not be returned to the caller.
-   *  @return EC_Normal if everything went fine, i.e.\ if request could be send and responses
-   *          (with whatever status) could be received.
-   */
-  virtual OFCondition sendMOVERequest(const T_ASC_PresentationContextID presID,
-                                      const OFString &moveDestinationAETitle,
-                                      DcmDataset *dataset,
-                                      OFList<RetrieveResponse*> *responses);
-
-  /** This is the standard handler for C-MOVE message responses: It just adds up all responses
-   *  it receives and prints a DEBUG message. Therefore, it is called for each response
-   *  received in sendMOVERequest(). The idea is of course to overwrite this function in a
-   *  derived, actual SCU implementation if required. Thus, after each response, the caller of
-   *  sendMOVERequest() can decide on its own whether he wants to cancel the C-MOVE session,
-   *  terminate the association, do something useful or whatever. Thus this function is a more
-   *  object-oriented kind of callback.
-   *  @param presID              [in]  The presentation context ID where the response was
-   *                                   received on.
-   *  @param response            [in]  The C-MOVE response received.
-   *  @param waitForNextResponse [out] Denotes whether SCU should try to receive another
-   *                                   response. If set to OFTrue, then sendMOVERequest() will
-   *                                   continue waiting for responses. The current
-   *                                   implementation does that for all responses do not have
-   *                                   status Failed, Warning, Success or unknown. If set to
-   *                                   OFFalse, sendMOVERequest() will return control to the
-   *                                   caller.
-   *  @return EC_Normal, if response could be handled. Error code otherwise.
-   *          The current implementation always returns EC_Normal.
-   */
-  virtual OFCondition handleMOVEResponse(const T_ASC_PresentationContextID presID,
-                                         RetrieveResponse *response,
-                                         OFBool &waitForNextResponse);
-
-  /** Sends a C-GET Request on given presentation context and receives list of responses. It
-   *  then switches control to the function handleCGETSession().
-   *  The full list of responses is returned to the caller. If he is not interested, he can
-   *  set responses=NULL when calling the function.
-   *  This function can be overwritten by actual SCU implementations but just should work fine
-   *  for most people.
-   *  @param presID    [in]  The presentation context ID that should be used. Must be an odd
-   *                         number.
-   *  @param dataset   [in]  The dataset containing the information about the
-   *                         object(s) to be retrieved
-   *  @param responses [out] The incoming C-GET responses for this request. If the caller
-   *                         specifies NULL, no responses will be returned; otherwise there
-   *                         should be at least one final C-GET response (mandatory). C-GET
-   *                         responses after each DICOM object received are optional and may
-   *                         have been omitted by the server.
-   *  @return EC_Normal if everything went fine, i.e.\ if request could be sent and expected
-   *          responses (with whatever status) could be received.
-   */
-  virtual OFCondition sendCGETRequest(const T_ASC_PresentationContextID presID,
-                                      DcmDataset *dataset,
-                                      OFList<RetrieveResponse*> *responses);
-
-  /** Does the logic for switching between C-GET Response and C-STORE Requests. Sends a C-GET
-   *  Request on given presentation context and receives list of responses. The full list of
-   *  responses is returned to the caller. If he is not interested, he can set responses=NULL
-   *  when calling the function. After sending a C-GET Request, there might be two different
-   *  responses coming in: C-GET-RSP (optional after each received object and mandatory after
-   *  the last object) or a mandatory C-STORE for each incoming object that is received due to
-   *  the request. This function therefore either calls handleCGETResponse() or
-   *  handleSTORERequest() in order to deal with the incoming message. All other messages lead
-   *  to an error within this handler.
-   *  This function can be overwritten by actual SCU implementations but just should work fine
-   *  for most people.
-   *  @param presID    [in]  The presentation context ID that should be used. Must be an odd
-   *                         number.
-   *  @param dataset   [in]  The dataset containing the information about the object(s) to be
-   *                         retrieved
-   *  @param responses [out] The incoming C-GET responses for this request. If the caller
-   *                         specifies NULL, no responses will be returned; otherwise there
-   *                         should be at least one final C-GET response (mandatory). C-GET
-   *                         responses after each DICOM object received are optional and may
-   *                         have been omitted by the server.
-   *  @return EC_Normal if everything went fine, i.e.\ if request could be send
-   *          and expected responses (with whatever status) could be received.
-   */
-  virtual OFCondition handleCGETSession(const T_ASC_PresentationContextID presID,
-                                        DcmDataset *dataset,
-                                        OFList<RetrieveResponse*> *responses);
-
-  /** Function handling a single C-GET Response. This standard handler reads the status of the
-   *  response and decides whether to receive any further messages related to the original
-   *  C-GET Request or whether the last response was received or an error occurred.
-   *  @param presID              [in]  The presentation context the C-GET Response was
-   *                                   received on.
-   *  @param response            [in]  The response received
-   *  @param continueCGETSession [out] Defines whether it is decided to wait for further C-GET
-   *                                   Responses/C-STORE Requests within this C-GET session
-   *  @return If no errors occur (dataset response NULL, SCU not connected), this method will
-   *          return EC_Normal, otherwise error code.
-   */
-  virtual OFCondition handleCGETResponse(const T_ASC_PresentationContextID presID,
-                                         RetrieveResponse* response,
-                                         OFBool &continueCGETSession);
-
-  /** Function handling a single C-STORE Request. If storage mode is set to disk (default),
-   *  this function is called and the incoming object stored to disk.
-   *  @param presID              [in]  The presentation context the C-STORE Request was
-   *                                   received on.
-   *  @param incomingObject      [in]  The dataset (the object) received. The function
-   *                                   takes ownership of the dataset, i.e. deletes it
-   *                                   after processing.
-   *  @param continueCGETSession [out] Defines whether it is decided to wait for further
-   *                                   C-GET Responses/C-STORE requests within this C-GET
-   *                                   session.
-   *  @param cStoreReturnStatus  [out] Denotes the desired C-STORE return status.
-   *  @return If errors occur (incomingObject NULL or SCU not connected or file could not be
-   *          stored), this method will return an error code otherwise EC_Normal.
-   */
-  virtual OFCondition handleSTORERequest(const T_ASC_PresentationContextID presID,
-                                         DcmDataset *incomingObject,
-                                         OFBool &continueCGETSession,
-                                         Uint16 &cStoreReturnStatus);
-
-  /** Function handling a single C-STORE Request. If storage mode is set to bit preserving,
-   *  this function is called and the incoming object stored directly to disk, i.e. not stored
-   *  fully in memory.
-   *  @param presID   [in] The presentation context the C-STORE Response was received on.
-   *  @param filename [in] The filename to store to
-   *  @param request  [in] The incoming C-STORE request command set
-   *  @return If errors occur (incomingObject NULL or SCU not connected filename not
-   *          specified), this method will return an error code otherwise EC_Normal.
-   */
-  virtual OFCondition handleSTORERequestFile(T_ASC_PresentationContextID *presID,
-                                             const OFString &filename,
-                                             T_DIMSE_C_StoreRQ *request);
-
-  /** Sends a C-FIND Request on given presentation context and receives list of responses.
-   *  The function receives the first response and then calls the function handleFINDResponse()
-   *  which gets the relevant presentation context together with the response dataset and
-   *  status information. Then it waits again for the next response, if there are more to
-   *  come (i.e. response status is PENDING). In the end, after receiving all responses, the
-   *  full list of responses is returned to the caller. If he is not interested, he just sets
-   *  responses=NULL when calling the function.
-   *  This function can be overwritten by actual SCU implementations but just should work fine
-   *  for most people.
-   *  @param presID    [in]  The presentation context ID that should be used. Must be an odd
-   *                         number.
-   *  @param queryKeys [in]  The dataset containing the query keys to be searched for on the
-   *                         server (SCP).
-   *  @param responses [out] The incoming C-FIND responses for this request. The caller is
-   *                         responsible for providing a non-NULL pointer for this case.
-   *                         After receiving the results, the caller is responsible for
-   *                         freeing the memory of this variable. If NULL is specified, the
-   *                         responses will be not returned to the caller.
-   *  @return EC_Normal if everything went fine, i.e.\ if request could be send and responses
-   *          (with whatever status) could be received.
-   */
-  virtual OFCondition sendFINDRequest(const T_ASC_PresentationContextID presID,
-                                      DcmDataset *queryKeys,
-                                      OFList<QRResponse*> *responses);
-
-  /** This is the standard handler for C-FIND message responses: It just adds up all responses
-   *  it receives and prints a DEBUG message. Therefore, it is called for each response
-   *  received in sendFINDRequest(). The idea is of course to overwrite this function in a
-   *  derived, actual SCU implementation if required. Thus, after each response, the caller of
-   *  sendFINDRequest() can decide on its own whether he wants to cancel the C-FIND session,
-   *  terminate the association, do something useful or whatever. That way this is a more
-   *  object-oriented kind of callback.
-   *  @param presID              [in]  The presentation context ID where the response was
-   *                                   received on.
-   *  @param response            [in]  The C-FIND response received.
-   *  @param waitForNextResponse [out] Denotes whether SCU should try to receive another
-   *                                   response. If set to OFTrue, then sendFINDRequest()
-   *                                   will continue waiting for responses. The current
-   *                                   implementation does that for all responses do not have
-   *                                   status SUCESSS. If set to OFFalse, sendFINDRequest()
-   *                                   will return control to the caller.
-   *  @return EC_Normal, if response could be handled. Error code otherwise.
-   *          The current implementation always returns EC_Normal.
-   */
-  virtual OFCondition handleFINDResponse(const T_ASC_PresentationContextID presID,
-                                         QRResponse *response,
-                                         OFBool &waitForNextResponse);
-
-  /** Send C-CANCEL and, therefore, ends the C-FIND -GET or -MOVE session, i.e.\ no further
-   *  responses will be handled. A call to this function only makes sense if an association
-   *  is open, the given presentation context represents a valid C-FIND/GET/MOVE-enabled SOP
-   *  class and usually only, if the last command send on that presentation context was a
-   *  C-FIND message.
-   *  @param presID [in] The presentation context ID where the C-CANCEL should be sent on.
-   *  @return The current implementation always returns EC_Normal.
-   */
-  virtual OFCondition sendCANCELRequest(const T_ASC_PresentationContextID presID);
-
-  /** This function sends a N-ACTION request on the currently opened association and receives
-   *  the corresponding response then
-   *  @param presID         [in]  The ID of the presentation context to be used for sending
-   *                              the request message. Should not be 0.
-   *  @param sopInstanceUID [in]  The requested SOP Instance UID
-   *  @param actionTypeID   [in]  The action type ID to be used
-   *  @param reqDataset     [in]  The dataset to be sent
-   *  @param rspStatusCode  [out] The response status code received. 0 means success,
-   *                              others can be found in the DICOM standard.
-   *  @return EC_Normal if request could be issued and response was received successfully,
-   *          an error code otherwise
-   */
-  virtual OFCondition sendACTIONRequest(const T_ASC_PresentationContextID presID,
-                                        const OFString &sopInstanceUID,
-                                        const Uint16 actionTypeID,
-                                        DcmDataset *reqDataset,
-                                        Uint16 &rspStatusCode);
-
-  /** This function sends N-EVENT-REPORT request and receives the corresponding response
-   *  @param presID         [in]  The ID of the presentation context to be used for sending
-   *                              the request message. Should not be 0.
-   *  @param sopInstanceUID [in]  The requested SOP Instance UID
-   *  @param eventTypeID    [in]  The event type ID to be used
-   *  @param reqDataset     [in]  The request dataset to be sent
-   *  @param rspStatusCode  [out] The response status code received. 0 means success,
-   *                              others can be found in the DICOM standard.
-   *  @return EC_Normal if request could be issued and response was received successfully,
-   *          an error code otherwise
-   */
-  virtual OFCondition sendEVENTREPORTRequest(const T_ASC_PresentationContextID presID,
-                                             const OFString &sopInstanceUID,
-                                             const Uint16 eventTypeID,
-                                             DcmDataset *reqDataset,
-                                             Uint16 &rspStatusCode);
-
-  /** Receives N-EVENT-REPORT request on the currently opened association and sends a
-   *  corresponding response. Calls checkEVENTREPORTRequest() in order to determine the
-   *  DIMSE status code to be used for the N-EVENT-REPORT response.
-   *  @param reqDataset  [out] Pointer to the dataset received
-   *  @param eventTypeID [out] Event Type ID from the command set received
-   *  @param timeout     [in]  Optional timeout in seconds for receiving data. This value
-   *                           (if not 0) overwrites the standard DIMSE timeout and also
-   *                           enables the non-blocking mode for receiving the request.
-   *  @return status, EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition handleEVENTREPORTRequest(DcmDataset *&reqDataset,
-                                               Uint16 &eventTypeID,
-                                               const int timeout = 0);
-
-  /** Closes the association created by this SCU. Also resets the current association.
-   *  @deprecated The use of this method is deprecated. Please use releaseAssociation()
-   *    or abortAssociation() instead.
-   *  @param closeType [in] Define whether to release or abort the association
-   */
-  virtual void closeAssociation(const DcmCloseAssociationType closeType);
-
-  /** Releases the current association by sending an A-RELEASE request to the SCP.
-   *  Please note that this release only applies to associations that have been
-   *  created by calling initNetwork() and negotiateAssociation().
-   *  @return status, EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition releaseAssociation();
-
-  /** Aborts the current association by sending an A-ABORT request to the SCP.
-   *  Please note that this abort only applies to associations that have been
-   *  created by calling initNetwork() and negotiateAssociation().
-   *  @return status, EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition abortAssociation();
-
-  /* Set methods */
-
-  /** Set maximum PDU length (to be received by SCU)
-   *  @param maxRecPDU [in] The maximum PDU size to use in bytes
-   */
-  void setMaxReceivePDULength(const Uint32 maxRecPDU);
-
-  /** Set whether to send in DIMSE blocking or non-blocking mode
-   *  @param blockingMode [in] Either blocking or non-blocking mode
-   */
-  void setDIMSEBlockingMode(const T_DIMSE_BlockingMode blockingMode);
-
-  /** Set SCU's AE title to be used in association negotiation
-   *  @param myAETtitle [in] The SCU's AE title to be used
-   */
-  void setAETitle(const OFString &myAETtitle);
-
-  /** Set SCP's host (host name or IP address) to talk to in association negotiation
-   *  @param peerHostName [in] The SCP's hostname or IP address to be used
-   */
-  void setPeerHostName(const OFString &peerHostName);
-
-  /** Set SCP's AE title to talk to in association negotiation
-   *  @param peerAETitle [in] The SCP's AE title to be used
-   */
-  void setPeerAETitle(const OFString &peerAETitle);
-
-  /** Set SCP's port number to connect to for association negotiation
-   *  @param peerPort [in] The SCP's port number
-   */
-  void setPeerPort(const Uint16 peerPort);
-
-  /** Set timeout for receiving DIMSE messages
-   *  @param dimseTimeout [in] DIMSE timeout in seconds for receiving data.
-   *                           If the blocking mode is DIMSE_NONBLOCKING the SCU
-   *                           will try to read data from the incoming socket stream
-   *                           for the number of seconds configured.
-   */
-  void setDIMSETimeout(const Uint32 dimseTimeout);
-
-  /** Set timeout for receiving ACSE messages
-   *  @param acseTimeout [in] ACSE timeout in seconds used by timer for message timeouts
-   *                          during association negotiation
-   */
-  void setACSETimeout(const Uint32 acseTimeout);
-
-  /** Set global timeout for connecting to the SCP. Note that this is a global
-   *  DCMTK setting i.e. it affects all code that uses dcmnet to start a DICOM
-   *  association to another host. Setting the timeout to -1 sets an infinite timeout,
-   *  i.e. any association request will wait forever (blocking) until the SCP accepts
-   *  the connection request. A value of 0 lets the SCU return immediately if the SCP
-   *  is not reachable at the first attempt.
-   *  @param connectionTimeout [in] Connection Timeout in seconds when connecting
-   *                                to SCPs. -1 will wait forever (blocking mode).
-   */
-  void setConnectionTimeout(const Sint32 connectionTimeout);
-
-
-  /** Set an association configuration file and profile to be used
-   *  @param filename [in] File name of the association configuration file
-   *  @param profile  [in] Profile inside the association negotiation file
-   */
-  void setAssocConfigFileAndProfile(const OFString &filename,
-                                    const OFString &profile);
-
-  /** Set the directory that should be used by the standard C-GET handler to store objects
-   *  that come in with the corresponding C-STORE requests
-   *  @param storeDir [in] The directory to store to. It is checked in handleSTORERequest()
-   *                       whether the directory is writeable and readable. By default, the
-   *                       received objects are stored in the current working directory.
-   */
-  void setStorageDir(const OFString &storeDir);
-
-  /** Set the storage mode to be used. Default is DCMSCU_STORAGE_DISK.
-   *  @param storageMode The storage mode to be used.
-   */
-  void setStorageMode(const DcmStorageMode storageMode);
-
-  /** Set whether to show presentation contexts in verbose or debug mode
-   *  @param mode [in] Show presentation contexts in verbose mode if OFTrue. By default,
-   *                   the presentation contexts are shown in debug mode.
-   */
-  void setVerbosePCMode(const OFBool mode);
-
-  /** Set the mode that specifies whether the transfer syntax of the dataset can be changed
-   *  for network transmission. This mainly covers the compression/decompression of datasets,
-   *  which is disabled by default.
-   *  @param mode [in] Allow dataset conversion if OFTrue
-   */
-  void setDatasetConversionMode(const OFBool mode);
-
-  /** Set the mode that specifies whether the progress of sending and receiving DIMSE
-   *  messages is notified by calling notifySENDProgress() and notifyRECEIVEProgress(),
-   *  respectively. The progress notification is enabled by default.
-   *  @param mode [in] Disable progress notification if OFFalse
-   */
-  void setProgressNotificationMode(const OFBool mode);
-
-  /* Get methods */
-
-  /** Get current connection status
-   *  @return OFTrue if SCU is currently connected, OFFalse otherwise
-   */
-  OFBool isConnected() const;
-
-  /** Returns maximum PDU length configured to be received by SCU
-   *  @return Maximum PDU length in bytes
-   */
-  Uint32 getMaxReceivePDULength() const;
-
-  /** Returns whether DIMSE messaging is configured to be blocking or unblocking
-   *  @return The blocking mode configured
-   */
-  T_DIMSE_BlockingMode getDIMSEBlockingMode() const;
-
-  /** Returns the SCU's own configured AE title
-   *  @return The AE title configured for this SCU
-   */
-  const OFString &getAETitle() const;
-
-  /** Returns the SCP's (peer's) host configured
-   *  @return The host name (or IP) configured to be talked to
-   */
-  const OFString &getPeerHostName() const;
-
-  /** Returns the SCP's (peer's) AE title configured
-   *  @return The AE title configured to be talked to
-   */
-  const OFString &getPeerAETitle() const;
-
-  /** Returns the SCP's (peer's) TCP/IP port configured
-   *  @return The port configured to talked to
-   */
-  Uint16 getPeerPort() const;
-
-  /** Returns DIMSE timeout in seconds for receiving data. If the blocking
-   *  mode is DIMSE_NONBLOCKING the SCU will try to read data from
-   *  the incoming socket stream for the number of seconds configured.
-   *  @return The DIMSE timeout (in seconds) configured
-   */
-  Uint32 getDIMSETimeout() const;
-
-  /** Returns ACSE timeout in seconds used by timer for message timeouts during
-   *  association negotiation.
-   *  @return The ACSE timeout (in seconds) configured
-   */
-  Uint32 getACSETimeout() const;
-
-  /** Returns the timeout configured defining how long SCU will wait for the
-   *  SCP when requesting an association. -1 means infinite waiting (blocking),
-   *  0 means no waiting at all. Note that this is currently a global DCMTK setting.
-   *  @return The connection timeout (in seconds)
-   */
-  Sint32 getConnectionTimeout() const;
-
-  /** Returns the storage directory used for storing objects received with C-STORE requests
-   *  in the context of C-GET sessions. Default is empty string which refers to the current
-   *  working directory.
-   *  @return The storage directory
-   */
-  OFString getStorageDir() const;
-
-  /** Returns the storage mode enabled
-   *  @return The storage mode enabled
-   */
-  DcmStorageMode getStorageMode() const;
-
-  /** Returns the verbose presentation context mode configured specifying whether details
-   *  on the presentation contexts (negotiated during association setup) should be shown in
-   *  verbose or debug mode. The latter is the default.
-   *  @return The current verbose presentation context mode. Show details on the
-   *          presentation contexts on INFO log level (verbose) if OFTrue and on DEBUG
-   *          level if OFFalse.
-   */
-  OFBool getVerbosePCMode() const;
-
-  /** Returns the mode that specifies whether the transfer syntax of the dataset can be
-   *  changed for network transmission. This mainly covers the compression/decompression
-   *  of datasets, which is disabled by default.
-   *  @return The current dataset conversion mode, enabled if OFTrue
-   */
-  OFBool getDatasetConversionMode() const;
-
-  /** Returns the mode that specifies whether the progress of sending and receiving DIMSE
-   *  messages is notified by calling notifySENDProgress() and notifyRECEIVEProgress(),
-   *  respectively. The progress notification is enabled by default.
-   *  @return The current progress notification mode, enabled if OFTrue
-   */
-  OFBool getProgressNotificationMode() const;
-
-  /** Returns whether SCU is configured to create a TLS connection with the SCP
-   *  @return OFFalse for this class but may be overridden by derived classes
-   */
-  OFBool getTLSEnabled() const;
-
-  /** Deletes internal networking structures from memory */
-  void freeNetwork();
+    /** Virtual destructor
+     */
+    virtual ~DcmSCU();
+
+    /** Add presentation context to be used for association negotiation
+     *  @param abstractSyntax [in] Abstract syntax name in UID format
+     *  @param xferSyntaxes   [in] List of transfer syntaxes to be added for the given abstract
+     *                             syntax
+     *  @param role           [in] The role to be negotiated
+     *  @return EC_Normal if adding was successful, otherwise error code
+     */
+    OFCondition addPresentationContext(const OFString& abstractSyntax,
+                                       const OFList<OFString>& xferSyntaxes,
+                                       const T_ASC_SC_ROLE role = ASC_SC_ROLE_DEFAULT);
+
+    /** Initialize network, i.e.\ prepare for association negotiation. If the SCU is already
+     *  connected, the call will not be successful and the old connection keeps open.
+     *  @return EC_Normal if initialization was successful, otherwise error code.
+     *          NET_EC_AlreadyConnected if SCU is already connected.
+     */
+    virtual OFCondition initNetwork();
 
-protected:
+    /** Negotiate association by using presentation contexts and parameters as defined by
+     *  earlier function calls. If negotiation fails, there is no need to close the association
+     *  or to do anything else with this class.
+     *  @return EC_Normal if negotiation was successful, otherwise error code.
+     *          NET_EC_AlreadyConnected if SCU is already connected.
+     */
+    virtual OFCondition negotiateAssociation();
+
+    /** After negotiation association, this call returns the first usable presentation context
+     *  given the desired abstract syntax and transfer syntax
+     *  @param abstractSyntax [in] The abstract syntax (UID) to look for
+     *  @param transferSyntax [in] The transfer syntax (UID) to look for. If empty, the transfer
+     *                             syntax is not checked.
+     *  @param requestorRole  [in] The role to look for (denoting the role the association
+     *                             requestor plays)
+     *  @return Adequate Presentation context ID that can be used. 0 if none found.
+     */
+    T_ASC_PresentationContextID findPresentationContextID(const OFString& abstractSyntax,
+                                                          const OFString& transferSyntax,
+                                                          const T_ASC_SC_ROLE requestorRole = ASC_SC_ROLE_DEFAULT);
+
+    /** After a successful association negotiation, this function is called to return the
+     *  presentation context ID that best matches the desired abstract syntax and transfer
+     *  syntax (TS). The function tries to do the following:
+     *  - If possible finds a presentation context with matching TS
+     *  - Else then tries to find an explicit VR uncompressed TS presentation context
+     *  - Else then tries to find an implicit VR uncompressed TS presentation context
+     *  - Else finally accepts each matching presentation ctx independent of TS.
+     *  @warning This method does not support filtering for a specific role, yet.
+     *  @param abstractSyntax [in] The abstract syntax (UID) to look for
+     *  @param transferSyntax [in] The transfer syntax (UID) to look for. If empty, the transfer
+     *                             syntax is not checked.
+     *  @return Adequate Presentation context ID that can be used. 0 if no appropriate
+     *  presentation context could be found at all.
+     */
+    T_ASC_PresentationContextID findAnyPresentationContextID(const OFString& abstractSyntax,
+                                                             const OFString& transferSyntax);
+
+    /** This function sends a C-ECHO command via network to another DICOM application
+     *  @param presID [in] Presentation context ID to use. A value of 0 lets SCP class tries
+     *                     to choose one on its own.
+     *  @return EC_Normal if echo was successful, an error code otherwise
+     *
+     */
+    virtual OFCondition sendECHORequest(const T_ASC_PresentationContextID presID);
+
+    /** This function sends a C-STORE request on the currently opened association and receives
+     *  the corresponding response then. If required and supported, the dataset of the SOP
+     *  instance can be converted automatically to the network transfer syntax that was
+     *  negotiated (and is specified by the parameter 'presID'). However, this feature is
+     *  disabled by default. See setDatasetConversionMode() on how to enable it.
+     *  @param presID        [in]  Contains in the end the ID of the presentation context which
+     *                             was specified in the DIMSE command. If 0 is given, the
+     *                             function tries to find an appropriate presentation context
+     *                             itself (based on SOP class and original transfer syntax of
+     *                             the 'dicomFile' or 'dataset').
+     *  @param dicomFile     [in]  The filename of the DICOM file to be sent. Alternatively, a
+     *                             dataset can be given in the next parameter. If both are given
+     *                             the dataset from the file name is used.
+     *  @param dataset       [in]  The dataset to be sent. Alternatively, a filename can be
+     *                             specified in the previous parameter. If both are given the
+     *                             dataset from the filename is used.
+     *  @param rspStatusCode [out] The response status code received. 0 means success, others
+     *                             can be found in the DICOM standard.
+     *  @param moveOriginatorAETitle [in] If this C-STORE is started due to a C-MOVE request,
+     *                               this parameter informs the C-STORE SCP about the C-MOVE
+     *                               client's AE title.
+     *  @param moveOriginatorMsgID   [in] If this C-STORE is started due to a C-MOVE request,
+     *                               this parameter informs the C-STORE SCP about the C-MOVE
+     *                               message ID.
+     *  @return EC_Normal if request could be issued and response was received successfully,
+     *          error code otherwise. That means that if the receiver sends a response denoting
+     *          failure of the storage request, EC_Normal will be returned.
+     */
+    virtual OFCondition sendSTORERequest(const T_ASC_PresentationContextID presID,
+                                         const OFFilename& dicomFile,
+                                         DcmDataset* dataset,
+                                         Uint16& rspStatusCode,
+                                         const OFString& moveOriginatorAETitle = "",
+                                         const Uint16 moveOriginatorMsgID      = 0);
+
+    /** Sends a C-MOVE Request on given presentation context and receives list of responses.
+     *  The function receives the first response and then calls the function handleMOVEResponse()
+     *  which gets the relevant presentation context together with the response dataset and
+     *  status information. Then it waits again for the next response, if there are more to
+     *  come (i.e. response status is PENDING). In the end, after receiving all responses, the
+     *  full list of responses is returned to the caller. If he is not interested, he just sets
+     *  responses=NULL when calling the function.
+     *  This function can be overwritten by actual SCU implementations but just should work fine
+     *  for most people.
+     *  @param presID                 [in]  The presentation context ID that should be used.
+     *                                      Must be an odd number.
+     *  @param moveDestinationAETitle [in]  The move destination's AE title, i.e.\ the one that
+     *                                      is used for connection to the storage server.
+     *  @param dataset                [in]  The dataset containing the information about the
+     *                                      object(s) to be retrieved.
+     *  @param responses              [out] The incoming C-MOVE responses for this request.
+     *                                      The caller is responsible for providing a non-NULL
+     *                                      pointer for this case. After receiving the results,
+     *                                      the caller is responsible for freeing the memory of
+     *                                      this variable. If NULL is specified, the responses
+     *                                      will not be returned to the caller.
+     *  @return EC_Normal if everything went fine, i.e.\ if request could be send and responses
+     *          (with whatever status) could be received.
+     */
+    virtual OFCondition sendMOVERequest(const T_ASC_PresentationContextID presID,
+                                        const OFString& moveDestinationAETitle,
+                                        DcmDataset* dataset,
+                                        OFList<RetrieveResponse*>* responses);
+
+    /** This is the standard handler for C-MOVE message responses: It just adds up all responses
+     *  it receives and prints a DEBUG message. Therefore, it is called for each response
+     *  received in sendMOVERequest(). The idea is of course to overwrite this function in a
+     *  derived, actual SCU implementation if required. Thus, after each response, the caller of
+     *  sendMOVERequest() can decide on its own whether he wants to cancel the C-MOVE session,
+     *  terminate the association, do something useful or whatever. Thus this function is a more
+     *  object-oriented kind of callback.
+     *  @param presID              [in]  The presentation context ID where the response was
+     *                                   received on.
+     *  @param response            [in]  The C-MOVE response received.
+     *  @param waitForNextResponse [out] Denotes whether SCU should try to receive another
+     *                                   response. If set to OFTrue, then sendMOVERequest() will
+     *                                   continue waiting for responses. The current
+     *                                   implementation does that for all responses do not have
+     *                                   status Failed, Warning, Success or unknown. If set to
+     *                                   OFFalse, sendMOVERequest() will return control to the
+     *                                   caller.
+     *  @return EC_Normal, if response could be handled. Error code otherwise.
+     *          The current implementation always returns EC_Normal.
+     */
+    virtual OFCondition handleMOVEResponse(const T_ASC_PresentationContextID presID,
+                                           RetrieveResponse* response,
+                                           OFBool& waitForNextResponse);
+
+    /** Sends a C-GET Request on given presentation context and receives list of responses. It
+     *  then switches control to the function handleCGETSession().
+     *  The full list of responses is returned to the caller. If he is not interested, he can
+     *  set responses=NULL when calling the function.
+     *  This function can be overwritten by actual SCU implementations but just should work fine
+     *  for most people.
+     *  @param presID    [in]  The presentation context ID that should be used. Must be an odd
+     *                         number.
+     *  @param dataset   [in]  The dataset containing the information about the
+     *                         object(s) to be retrieved
+     *  @param responses [out] The incoming C-GET responses for this request. If the caller
+     *                         specifies NULL, no responses will be returned; otherwise there
+     *                         should be at least one final C-GET response (mandatory). C-GET
+     *                         responses after each DICOM object received are optional and may
+     *                         have been omitted by the server.
+     *  @return EC_Normal if everything went fine, i.e.\ if request could be sent and expected
+     *          responses (with whatever status) could be received.
+     */
+    virtual OFCondition sendCGETRequest(const T_ASC_PresentationContextID presID,
+                                        DcmDataset* dataset,
+                                        OFList<RetrieveResponse*>* responses);
+
+    /** Does the logic for switching between C-GET Response and C-STORE Requests. Sends a C-GET
+     *  Request on given presentation context and receives list of responses. The full list of
+     *  responses is returned to the caller. If he is not interested, he can set responses=NULL
+     *  when calling the function. After sending a C-GET Request, there might be two different
+     *  responses coming in: C-GET-RSP (optional after each received object and mandatory after
+     *  the last object) or a mandatory C-STORE for each incoming object that is received due to
+     *  the request. This function therefore either calls handleCGETResponse() or
+     *  handleSTORERequest() in order to deal with the incoming message. All other messages lead
+     *  to an error within this handler.
+     *  This function can be overwritten by actual SCU implementations but just should work fine
+     *  for most people.
+     *  @param presID    [in]  The presentation context ID that should be used. Must be an odd
+     *                         number.
+     *  @param dataset   [in]  The dataset containing the information about the object(s) to be
+     *                         retrieved
+     *  @param responses [out] The incoming C-GET responses for this request. If the caller
+     *                         specifies NULL, no responses will be returned; otherwise there
+     *                         should be at least one final C-GET response (mandatory). C-GET
+     *                         responses after each DICOM object received are optional and may
+     *                         have been omitted by the server.
+     *  @return EC_Normal if everything went fine, i.e.\ if request could be send
+     *          and expected responses (with whatever status) could be received.
+     */
+    virtual OFCondition handleCGETSession(const T_ASC_PresentationContextID presID,
+                                          DcmDataset* dataset,
+                                          OFList<RetrieveResponse*>* responses);
+
+    /** Function handling a single C-GET Response. This standard handler reads the status of the
+     *  response and decides whether to receive any further messages related to the original
+     *  C-GET Request or whether the last response was received or an error occurred.
+     *  @param presID              [in]  The presentation context the C-GET Response was
+     *                                   received on.
+     *  @param response            [in]  The response received
+     *  @param continueCGETSession [out] Defines whether it is decided to wait for further C-GET
+     *                                   Responses/C-STORE Requests within this C-GET session
+     *  @return If no errors occur (dataset response NULL, SCU not connected), this method will
+     *          return EC_Normal, otherwise error code.
+     */
+    virtual OFCondition handleCGETResponse(const T_ASC_PresentationContextID presID,
+                                           RetrieveResponse* response,
+                                           OFBool& continueCGETSession);
+
+    /** Function handling a single C-STORE Request. If storage mode is set to disk (default),
+     *  this function is called and the incoming object stored to disk.
+     *  @param presID              [in]  The presentation context the C-STORE Request was
+     *                                   received on.
+     *  @param incomingObject      [in]  The dataset (the object) received. The function
+     *                                   takes ownership of the dataset, i.e. deletes it
+     *                                   after processing.
+     *  @param continueCGETSession [out] Defines whether it is decided to wait for further
+     *                                   C-GET Responses/C-STORE requests within this C-GET
+     *                                   session.
+     *  @param cStoreReturnStatus  [out] Denotes the desired C-STORE return status.
+     *  @return If errors occur (incomingObject NULL or SCU not connected or file could not be
+     *          stored), this method will return an error code otherwise EC_Normal.
+     */
+    virtual OFCondition handleSTORERequest(const T_ASC_PresentationContextID presID,
+                                           DcmDataset* incomingObject,
+                                           OFBool& continueCGETSession,
+                                           Uint16& cStoreReturnStatus);
+
+    /** Function handling a single C-STORE Request. If storage mode is set to bit preserving,
+     *  this function is called and the incoming object stored directly to disk, i.e. not stored
+     *  fully in memory.
+     *  @param presID   [in] The presentation context the C-STORE Response was received on.
+     *  @param filename [in] The filename to store to
+     *  @param request  [in] The incoming C-STORE request command set
+     *  @return If errors occur (incomingObject NULL or SCU not connected filename not
+     *          specified), this method will return an error code otherwise EC_Normal.
+     */
+    virtual OFCondition
+    handleSTORERequestFile(T_ASC_PresentationContextID* presID, const OFString& filename, T_DIMSE_C_StoreRQ* request);
+
+    /** Sends a C-FIND Request on given presentation context and receives list of responses.
+     *  The function receives the first response and then calls the function handleFINDResponse()
+     *  which gets the relevant presentation context together with the response dataset and
+     *  status information. Then it waits again for the next response, if there are more to
+     *  come (i.e. response status is PENDING). In the end, after receiving all responses, the
+     *  full list of responses is returned to the caller. If he is not interested, he just sets
+     *  responses=NULL when calling the function.
+     *  This function can be overwritten by actual SCU implementations but just should work fine
+     *  for most people.
+     *  @param presID    [in]  The presentation context ID that should be used. Must be an odd
+     *                         number.
+     *  @param queryKeys [in]  The dataset containing the query keys to be searched for on the
+     *                         server (SCP).
+     *  @param responses [out] The incoming C-FIND responses for this request. The caller is
+     *                         responsible for providing a non-NULL pointer for this case.
+     *                         After receiving the results, the caller is responsible for
+     *                         freeing the memory of this variable. If NULL is specified, the
+     *                         responses will be not returned to the caller.
+     *  @return EC_Normal if everything went fine, i.e.\ if request could be send and responses
+     *          (with whatever status) could be received.
+     */
+    virtual OFCondition
+    sendFINDRequest(const T_ASC_PresentationContextID presID, DcmDataset* queryKeys, OFList<QRResponse*>* responses);
+
+    /** This is the standard handler for C-FIND message responses: It just adds up all responses
+     *  it receives and prints a DEBUG message. Therefore, it is called for each response
+     *  received in sendFINDRequest(). The idea is of course to overwrite this function in a
+     *  derived, actual SCU implementation if required. Thus, after each response, the caller of
+     *  sendFINDRequest() can decide on its own whether he wants to cancel the C-FIND session,
+     *  terminate the association, do something useful or whatever. That way this is a more
+     *  object-oriented kind of callback.
+     *  @param presID              [in]  The presentation context ID where the response was
+     *                                   received on.
+     *  @param response            [in]  The C-FIND response received.
+     *  @param waitForNextResponse [out] Denotes whether SCU should try to receive another
+     *                                   response. If set to OFTrue, then sendFINDRequest()
+     *                                   will continue waiting for responses. The current
+     *                                   implementation does that for all responses do not have
+     *                                   status SUCCESS. If set to OFFalse, sendFINDRequest()
+     *                                   will return control to the caller.
+     *  @return EC_Normal, if response could be handled. Error code otherwise.
+     *          The current implementation always returns EC_Normal.
+     */
+    virtual OFCondition
+    handleFINDResponse(const T_ASC_PresentationContextID presID, QRResponse* response, OFBool& waitForNextResponse);
+
+    /** Send C-CANCEL and, therefore, ends the C-FIND -GET or -MOVE session, i.e.\ no further
+     *  responses will be handled. A call to this function only makes sense if an association
+     *  is open, the given presentation context represents a valid C-FIND/GET/MOVE-enabled SOP
+     *  class and usually only, if the last command send on that presentation context was a
+     *  C-FIND message.
+     *  @param presID [in] The presentation context ID where the C-CANCEL should be sent on.
+     *  @return The current implementation always returns EC_Normal.
+     */
+    virtual OFCondition sendCANCELRequest(const T_ASC_PresentationContextID presID);
+
+    /** This function sends a N-ACTION request on the currently opened association and receives
+     *  the corresponding response then
+     *  @param presID         [in]  The ID of the presentation context to be used for sending
+     *                              the request message. Should not be 0.
+     *  @param sopInstanceUID [in]  The requested SOP Instance UID
+     *  @param actionTypeID   [in]  The action type ID to be used
+     *  @param reqDataset     [in]  The dataset to be sent
+     *  @param rspStatusCode  [out] The response status code received. 0 means success,
+     *                              others can be found in the DICOM standard.
+     *  @return EC_Normal if request could be issued and response was received successfully,
+     *          an error code otherwise
+     */
+    virtual OFCondition sendACTIONRequest(const T_ASC_PresentationContextID presID,
+                                          const OFString& sopInstanceUID,
+                                          const Uint16 actionTypeID,
+                                          DcmDataset* reqDataset,
+                                          Uint16& rspStatusCode);
+
+    /** This function sends N-EVENT-REPORT request and receives the corresponding response
+     *  @param presID         [in]  The ID of the presentation context to be used for sending
+     *                              the request message. Should not be 0.
+     *  @param sopInstanceUID [in]  The requested SOP Instance UID
+     *  @param eventTypeID    [in]  The event type ID to be used
+     *  @param reqDataset     [in]  The request dataset to be sent
+     *  @param rspStatusCode  [out] The response status code received. 0 means success,
+     *                              others can be found in the DICOM standard.
+     *  @return EC_Normal if request could be issued and response was received successfully,
+     *          an error code otherwise
+     */
+    virtual OFCondition sendEVENTREPORTRequest(const T_ASC_PresentationContextID presID,
+                                               const OFString& sopInstanceUID,
+                                               const Uint16 eventTypeID,
+                                               DcmDataset* reqDataset,
+                                               Uint16& rspStatusCode);
+
+    /** Receives N-EVENT-REPORT request on the currently opened association and sends a
+     *  corresponding response. Calls checkEVENTREPORTRequest() in order to determine the
+     *  DIMSE status code to be used for the N-EVENT-REPORT response.
+     *  @param reqDataset  [out] Pointer to the dataset received
+     *  @param eventTypeID [out] Event Type ID from the command set received
+     *  @param timeout     [in]  Optional timeout in seconds for receiving data. This value
+     *                           (if not 0) overwrites the standard DIMSE timeout and also
+     *                           enables the non-blocking mode for receiving the request.
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition handleEVENTREPORTRequest(DcmDataset*& reqDataset, Uint16& eventTypeID, const int timeout = 0);
+
+    /** Function handling a single C-GET, C-FIND or C-MOVE Response, used by
+     *  handleCGETResponse(), handleFINDResponse() and handleMOVEResponse().
+     *  It prints a message to the logger (warning, error or debug level related
+     *  to the status code provided) and sets waitForNextResponse if the status
+     *  provided is a DIMSE pending status.
+     *  @param dimseStatus         [in]  The DIMSE status code to handle
+     *  @param message             [in]  The message to be printed
+     *  @param waitForNextResponse [out] Defines whether it is decided to wait for further
+     *                                   Responses with the C-GET/FIND/MOVE session.
+     *  @return If no processing errors occurs this method will return EC_Normal,
+     *          otherwise an error code.
+     */
+    virtual OFCondition
+    handleSessionResponseDefault(const Uint16 dimseStatus, const OFString& message, OFBool& waitForNextResponse);
 
-  /** Sends a DIMSE command and possibly also a dataset from a data object via network to
-   *  another DICOM application
-   *  @param presID     [in]  Presentation context ID to be used for message
-   *  @param msg        [in]  Structure that represents a certain DIMSE command which
-   *                          shall be sent
-   *  @param dataObject [in]  The instance data which shall be sent to the other DICOM
-   *                          application; NULL, if there is none
-   *  @param commandSet [out] If this parameter is not NULL it will return a copy of the
-   *                          DIMSE command which is sent to the other DICOM application
-   *  @return EC_Normal if sending request was successful, an error code otherwise
-   */
-  OFCondition sendDIMSEMessage(const T_ASC_PresentationContextID presID,
-                               T_DIMSE_Message *msg,
-                               DcmDataset *dataObject,
-                               DcmDataset **commandSet = NULL);
-
-  /** Returns SOP Class UID, SOP Instance UID and original transfer syntax for a given dataset.
-   *  If the dataset is NULL, all returned values will be undefined (i.e. empty or EXS_Unknown).
-   *  @param dataset        [in]  The dataset to read from
-   *  @param sopClassUID    [out] The value of attribute SOP Class UID if present
-   *  @param sopInstanceUID [out] The value of attribute SOP Instance UID if present
-   *  @param transferSyntax [out] The value of transfer syntax that originally was read from
-   *                              disk. Will be unknown if the dataset was created in memory.
-   *  @return EC_Normal if all information could be retrieved and is valid, an error code
-   *    otherwise
-   */
-  OFCondition getDatasetInfo(DcmDataset *dataset,
-                             OFString &sopClassUID,
-                             OFString &sopInstanceUID,
-                             E_TransferSyntax &transferSyntax);
-
-  /** Tells DcmSCU to use a secure TLS connection described by the given TLS layer
-   *  @param tlayer [in] The TLS transport layer including all TLS parameters
-   *  @return EC_Normal if given transport layer is ok, an error code otherwise
-   */
-  OFCondition useSecureConnection(DcmTransportLayer *tlayer);
-
-  /** Receive DIMSE command (excluding dataset!) over the currently open association
-   *  @param presID       [out] Contains in the end the ID of the presentation context
-   *                            which was specified in the DIMSE command received
-   *  @param msg          [out] The message received
-   *  @param statusDetail [out] If a non-NULL value is passed this variable will in the end
-   *                            contain detailed information with regard to the status
-   *                            information which is captured in the status element
-   *                            (0000,0900). Note that the value for element (0000,0900) is
-   *                            not contained in this return value but in internal msg. For
-   *                            details on the structure of this object, see DICOM standard
-   *                            part 7, annex C).
-   *  @param commandSet   [out] If this parameter is not NULL, it will return a copy of the
-   *                            DIMSE command which was received from the other DICOM
-   *                            application. The caller is responsible to de-allocate the
-   *                            returned object!
-   *  @param timeout      [in]  If this parameter is not 0, it specifies the timeout (in
-   *                            seconds) to be used for receiving the DIMSE command.
-   *                            Otherwise, the default timeout value is used (see
-   *                            setDIMSETimeout()).
-   *  @return EC_Normal if command could be received successfully, an error code otherwise
-   */
-  OFCondition receiveDIMSECommand(T_ASC_PresentationContextID *presID,
-                                  T_DIMSE_Message *msg,
-                                  DcmDataset **statusDetail,
-                                  DcmDataset **commandSet = NULL,
-                                  const Uint32 timeout = 0);
-
-  /** Receives one dataset (of instance data) via network from another DICOM application
-   *  @param presID     [out] Contains in the end the ID of the presentation context which
-   *                          was used in the PDVs that were received on the network. If the
-   *                          PDVs show different presentation context IDs, this function
-   *                          will return an error.
-   *  @param dataObject [out] Contains in the end the information which was received over
-   *                          the network
-   *  @return EC_Normal if dataset could be received successfully, an error code otherwise
-   */
-  OFCondition receiveDIMSEDataset(T_ASC_PresentationContextID *presID,
-                                  DcmDataset **dataObject);
-
-  /** clear list of presentation contexts. In addition, any currently selected association
-   *  configuration file is disabled.
-   */
-  void clearPresentationContexts();
-
-   /** After negotiation association, this call returns the presentation context belonging
-    *  to the given presentation context ID
-    *  @param presID         [in]  The presentation context ID to look for
-    *  @param abstractSyntax [out] The abstract syntax (UID) for that ID.
-    *                              Empty, if such a presentation context does not exist.
-    *  @param transferSyntax [out] The transfer syntax (UID) for that ID.
-    *                              Empty, if such a presentation context does not exist.
-    */
-  void findPresentationContext(const T_ASC_PresentationContextID presID,
-                               OFString &abstractSyntax,
-                               OFString &transferSyntax);
-
-  /* ***********************************************************************
-   *  Functions particularly interesting for overwriting in derived classes
-   * *********************************************************************** */
-
-  /** This function is called if an object was received due to a C-GET request and can be
-   *  overwritten by a user in order to be informed about such an event. The default
-   *  implementation just prints a DEBUG message. Note that this function is not called if
-   *  the SCU is in storage mode DCMSCU_STORAGE_IGNORE.
-   *  @param filename       [in] The filename written
-   *  @param sopClassUID    [in] The SOP Class UID of the object written
-   *  @param sopInstanceUID [in] The SOP Instance UID of the object written
-   */
-  virtual void notifyInstanceStored(const OFString &filename,
-                                    const OFString &sopClassUID,
-                                    const OFString &sopInstanceUID) const;
-
-  /** This function is called while sending DIMSE messages, i.e.\ on each PDV of a dataset.
-   *  The default implementation just prints a TRACE message on the number of bytes sent so
-   *  far. By overwriting this method, the progress of the send process can be shown to the
-   *  user in a more appropriate way. The progress notification can also be disabled
-   *  completely by calling setProgressNotificationMode().
-   *  @param byteCount [in] Number of bytes sent so far
-   */
-  virtual void notifySENDProgress(const unsigned long byteCount);
-
-  /** This function is called while receiving DIMSE messages, i.e.\ on each PDV of a dataset.
-   *  The default implementation just prints a TRACE message on the number of bytes received
-   *  so far. By overwriting this method, the progress of the receive process can be shown to
-   *  the user in a more appropriate way. The progress notification can also be disabled
-   *  completely by calling setProgressNotificationMode().
-   *  @param byteCount [in] Number of bytes received so far
-   */
-  virtual void notifyRECEIVEProgress(const unsigned long byteCount);
-
-  /** Check given N-EVENT-REPORT request and dataset for validity. This method is called by
-   *  handleEVENTREPORTRequest() before sending the response in order to determine the
-   *  DIMSE status code to be used for the response message.
-   *  @param request    [in] The N-EVENT-REPORT request message data structure
-   *  @param reqDataset [in] The N-EVENT-REPORT request dataset received. Might be NULL.
-   *  @return DIMSE status code to be used for the N-EVENT-REPORT response.
-   *          Always returns STATUS_Success (0). Derived classes should, therefore,
-   *          overwrite this method and return a more appropriate value based on the
-   *          result of the checks performed.
-   */
-  virtual Uint16 checkEVENTREPORTRequest(T_DIMSE_N_EventReportRQ &request,
-                                         DcmDataset *reqDataset);
-
-  /** Sends back a C-STORE response on the given presentation context, with the designated
-   *  status, fitting the corresponding C-STORE request.
-   *  @param presID  [in] The presentation context ID to be used.
-   *  @param status  [in] The storage DIMSE status to be used.
-   *  @param request [in] The C-STORE request that should be responded to.
-   *  @result EC_Normal if the response could be sent, error otherwise.
-   */
-  virtual OFCondition sendSTOREResponse(T_ASC_PresentationContextID presID,
-                                        Uint16 status,
-                                        const T_DIMSE_C_StoreRQ &request);
-
-  /** Helper function that generates a storage filename by extracting SOP Class and SOP
-   *  Instance UID from a dataset and combining that with the configured storage directory.
-   *  The SOP class is used to create an initial two letter abbreviation for the
-   *  corresponding modality, e.g. CT. An example for a storage filename created by this
-   *  function is "/storage_dir/CT.1.2.3.4.5" for a CT with SOP Instance UID "1.2.3.4.5".
-   *  This function might be overwritten to change the filename behaviour completely. This
-   *  function is only called if the SCU is in DCMSCU_STORAGE_DISK mode.
-   *  @param dataset [in] The dataset that should be stored to disk
-   *  @result Non-empty string if successful, otherwise empty string.
-   */
-  virtual OFString createStorageFilename(DcmDataset *dataset);
-
-  /** Receives a DICOM dataset on a given presentation context ID but does not store it in
-   *  memory or disk, thus ignoring it.
-   *  @param presID  [in] The presentation context to be used
-   *  @param request [in] The corresponding C-STORE request
-   *  @return EC_Normal if ignoring worked, error code otherwise.
-   */
-  virtual OFCondition ignoreSTORERequest(T_ASC_PresentationContextID presID,
-                                         const T_DIMSE_C_StoreRQ &request);
-
-  /* Callback functions (static) */
-
-  /** Callback function used for sending DIMSE messages.
-   *  @param callbackContext [in] The desired user callback data
-   *  @param byteCount       [in] Progress bytes count
-   */
-  static void callbackSENDProgress(void *callbackContext,
-                                   unsigned long byteCount);
-
-  /** Callback function used for receiving DIMSE messages.
-   *  @param callbackContext [in] The desired user callback data
-   *  @param byteCount       [in] Progress bytes count
-   */
-  static void callbackRECEIVEProgress(void *callbackContext,
-                                      unsigned long byteCount);
+    /** Closes the association created by this SCU. Also resets the current association.
+     *  @deprecated The use of this method is deprecated. Please use releaseAssociation()
+     *    or abortAssociation() instead.
+     *  @param closeType [in] Define whether to release or abort the association
+     */
+    virtual void closeAssociation(const DcmCloseAssociationType closeType);
 
-private:
+    /** Releases the current association by sending an A-RELEASE request to the SCP.
+     *  Please note that this release only applies to associations that have been
+     *  created by calling initNetwork() and negotiateAssociation().
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition releaseAssociation();
 
-  /** Private undefined copy-constructor. Shall never be called.
-   *  @param src Source object
-   */
-  DcmSCU(const DcmSCU &src);
+    /** Aborts the current association by sending an A-ABORT request to the SCP.
+     *  Please note that this abort only applies to associations that have been
+     *  created by calling initNetwork() and negotiateAssociation().
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition abortAssociation();
 
-  /** Private undefined operator=. Shall never be called.
-   *  @param src Source object
-   *  @return Reference to this
-   */
-  DcmSCU &operator=(const DcmSCU &src);
+    /* Set methods */
 
-  /// Association of this SCU. This class only handles 1 association at a time.
-  T_ASC_Association *m_assoc;
+    /** Set maximum PDU length (to be received by SCU)
+     *  @param maxRecPDU [in] The maximum PDU size to use in bytes
+     */
+    void setMaxReceivePDULength(const Uint32 maxRecPDU);
 
-  /// The DICOM network the association is based on
-  T_ASC_Network *m_net;
+    /** Set whether to send in DIMSE blocking or non-blocking mode
+     *  @param blockingMode [in] Either blocking or non-blocking mode
+     */
+    void setDIMSEBlockingMode(const T_DIMSE_BlockingMode blockingMode);
 
-  /// Association parameters
-  T_ASC_Parameters *m_params;
+    /** Set SCU's AE title to be used in association negotiation
+     *  @param myAETtitle [in] The SCU's AE title to be used
+     */
+    void setAETitle(const OFString& myAETtitle);
 
-  /// Configuration file for presentation contexts (optional)
-  OFString m_assocConfigFilename;
+    /** Set SCP's host (host name or IP address) to talk to in association negotiation
+     *  @param peerHostName [in] The SCP's hostname or IP address to be used
+     */
+    void setPeerHostName(const OFString& peerHostName);
 
-  /// Profile in configuration file that should be used (optional)
-  OFString m_assocConfigProfile;
+    /** Set SCP's AE title to talk to in association negotiation
+     *  @param peerAETitle [in] The SCP's AE title to be used
+     */
+    void setPeerAETitle(const OFString& peerAETitle);
 
-  /// Defines presentation context, consisting of one abstract syntax name
-  /// and a list of transfer syntaxes for this abstract syntax
-  struct DCMTK_DCMNET_EXPORT DcmSCUPresContext {
-    /** Default constructor
+    /** Set SCP's port number to connect to for association negotiation
+     *  @param peerPort [in] The SCP's port number
      */
-    DcmSCUPresContext()
-    : abstractSyntaxName()
-    , transferSyntaxes()
-    , roleSelect(ASC_SC_ROLE_DEFAULT)
-    {
-    }
-    /// Abstract Syntax Name of Presentation Context
-    OFString abstractSyntaxName;
-    /// List of Transfer Syntaxes for Presentation Context
-    OFList<OFString> transferSyntaxes;
-    /// Role Selection
-    T_ASC_SC_ROLE roleSelect;
-  };
+    void setPeerPort(const Uint16 peerPort);
+
+    /** Set timeout for receiving DIMSE messages
+     *  @param dimseTimeout [in] DIMSE timeout in seconds for receiving data.
+     *                           If the blocking mode is DIMSE_NONBLOCKING the SCU
+     *                           will try to read data from the incoming socket stream
+     *                           for the number of seconds configured.
+     */
+    void setDIMSETimeout(const Uint32 dimseTimeout);
+
+    /** Set timeout for receiving ACSE messages
+     *  @param acseTimeout [in] ACSE timeout in seconds used by timer for message timeouts
+     *                          during association negotiation
+     */
+    void setACSETimeout(const Uint32 acseTimeout);
+
+    /** Set global timeout for connecting to the SCP. Note that this is a global
+     *  DCMTK setting i.e. it affects all code that uses dcmnet to start a DICOM
+     *  association to another host. Setting the timeout to -1 sets an infinite timeout,
+     *  i.e. any association request will wait forever (blocking) until the SCP accepts
+     *  the connection request. A value of 0 lets the SCU return immediately if the SCP
+     *  is not reachable at the first attempt.
+     *  @param connectionTimeout [in] Connection Timeout in seconds when connecting
+     *                                to SCPs. -1 will wait forever (blocking mode).
+     */
+    void setConnectionTimeout(const Sint32 connectionTimeout);
+
+    /** Set an association configuration file and profile to be used
+     *  @param filename [in] File name of the association configuration file
+     *  @param profile  [in] Profile inside the association negotiation file
+     */
+    void setAssocConfigFileAndProfile(const OFString& filename, const OFString& profile);
+
+    /** Set the directory that should be used by the standard C-GET handler to store objects
+     *  that come in with the corresponding C-STORE requests
+     *  @param storeDir [in] The directory to store to. It is checked in handleSTORERequest()
+     *                       whether the directory is writeable and readable. By default, the
+     *                       received objects are stored in the current working directory.
+     */
+    void setStorageDir(const OFString& storeDir);
+
+    /** Set the storage mode to be used. Default is DCMSCU_STORAGE_DISK.
+     *  @param storageMode The storage mode to be used.
+     */
+    void setStorageMode(const DcmStorageMode storageMode);
+
+    /** Set whether to show presentation contexts in verbose or debug mode
+     *  @param mode [in] Show presentation contexts in verbose mode if OFTrue. By default,
+     *                   the presentation contexts are shown in debug mode.
+     */
+    void setVerbosePCMode(const OFBool mode);
+
+    /** Set the mode that specifies whether the transfer syntax of the dataset can be changed
+     *  for network transmission. This mainly covers the compression/decompression of datasets,
+     *  which is disabled by default.
+     *  @param mode [in] Allow dataset conversion if OFTrue
+     */
+    void setDatasetConversionMode(const OFBool mode);
+
+    /** Set the mode that specifies whether the progress of sending and receiving DIMSE
+     *  messages is notified by calling notifySENDProgress() and notifyRECEIVEProgress(),
+     *  respectively. The progress notification is enabled by default.
+     *  @param mode [in] Disable progress notification if OFFalse
+     */
+    void setProgressNotificationMode(const OFBool mode);
+
+    /* Get methods */
+
+    /** Get current connection status
+     *  @return OFTrue if SCU is currently connected, OFFalse otherwise
+     */
+    OFBool isConnected() const;
+
+    /** Returns maximum PDU length configured to be received by SCU
+     *  @return Maximum PDU length in bytes
+     */
+    Uint32 getMaxReceivePDULength() const;
+
+    /** Returns whether DIMSE messaging is configured to be blocking or unblocking
+     *  @return The blocking mode configured
+     */
+    T_DIMSE_BlockingMode getDIMSEBlockingMode() const;
+
+    /** Returns the SCU's own configured AE title
+     *  @return The AE title configured for this SCU
+     */
+    const OFString& getAETitle() const;
+
+    /** Returns the SCP's (peer's) host configured
+     *  @return The host name (or IP) configured to be talked to
+     */
+    const OFString& getPeerHostName() const;
+
+    /** Returns the SCP's (peer's) AE title configured
+     *  @return The AE title configured to be talked to
+     */
+    const OFString& getPeerAETitle() const;
+
+    /** Returns the SCP's (peer's) TCP/IP port configured
+     *  @return The port configured to talked to
+     */
+    Uint16 getPeerPort() const;
+
+    /** Returns DIMSE timeout in seconds for receiving data. If the blocking
+     *  mode is DIMSE_NONBLOCKING the SCU will try to read data from
+     *  the incoming socket stream for the number of seconds configured.
+     *  @return The DIMSE timeout (in seconds) configured
+     */
+    Uint32 getDIMSETimeout() const;
 
-  /// List of presentation contexts that should be negotiated
-  OFList<DcmSCUPresContext> m_presContexts;
+    /** Returns ACSE timeout in seconds used by timer for message timeouts during
+     *  association negotiation.
+     *  @return The ACSE timeout (in seconds) configured
+     */
+    Uint32 getACSETimeout() const;
 
-  /// Configuration file containing association parameters
-  OFString m_assocConfigFile;
+    /** Returns the timeout configured defining how long SCU will wait for the
+     *  SCP when requesting an association. -1 means infinite waiting (blocking),
+     *  0 means no waiting at all. Note that this is currently a global DCMTK setting.
+     *  @return The connection timeout (in seconds)
+     */
+    Sint32 getConnectionTimeout() const;
 
-  /// The last DIMSE successfully sent, unresponded DIMSE request
-  T_DIMSE_Message *m_openDIMSERequest;
+    /** Returns the storage directory used for storing objects received with C-STORE requests
+     *  in the context of C-GET sessions. Default is empty string which refers to the current
+     *  working directory.
+     *  @return The storage directory
+     */
+    OFString getStorageDir() const;
 
-  /// Maximum PDU size (default: 16384 bytes)
-  Uint32 m_maxReceivePDULength;
+    /** Returns the storage mode enabled
+     *  @return The storage mode enabled
+     */
+    DcmStorageMode getStorageMode() const;
+
+    /** Returns the verbose presentation context mode configured specifying whether details
+     *  on the presentation contexts (negotiated during association setup) should be shown in
+     *  verbose or debug mode. The latter is the default.
+     *  @return The current verbose presentation context mode. Show details on the
+     *          presentation contexts on INFO log level (verbose) if OFTrue and on DEBUG
+     *          level if OFFalse.
+     */
+    OFBool getVerbosePCMode() const;
 
-  /// DIMSE blocking mode (default: blocking)
-  T_DIMSE_BlockingMode m_blockMode;
+    /** Returns the mode that specifies whether the transfer syntax of the dataset can be
+     *  changed for network transmission. This mainly covers the compression/decompression
+     *  of datasets, which is disabled by default.
+     *  @return The current dataset conversion mode, enabled if OFTrue
+     */
+    OFBool getDatasetConversionMode() const;
 
-  /// AE title of this application (default: ANY-SCU)
-  OFString m_ourAETitle;
+    /** Returns the mode that specifies whether the progress of sending and receiving DIMSE
+     *  messages is notified by calling notifySENDProgress() and notifyRECEIVEProgress(),
+     *  respectively. The progress notification is enabled by default.
+     *  @return The current progress notification mode, enabled if OFTrue
+     */
+    OFBool getProgressNotificationMode() const;
 
-  /// Peer host (IP or host name)
-  OFString m_peer;
+    /** Returns whether SCU is configured to create a TLS connection with the SCP
+     *  @return OFFalse for this class but may be overridden by derived classes
+     */
+    OFBool getTLSEnabled() const;
 
-  /// AE title of remote application (default: ANY-SCP)
-  OFString m_peerAETitle;
+    /** Deletes internal networking structures from memory */
+    void freeNetwork();
 
-  /// Port of remote application entity (default: 104)
-  Uint16 m_peerPort;
+protected:
+    /** Sends a DIMSE command and possibly also a dataset from a data object via network to
+     *  another DICOM application
+     *  @param presID     [in]  Presentation context ID to be used for message
+     *  @param msg        [in]  Structure that represents a certain DIMSE command which
+     *                          shall be sent
+     *  @param dataObject [in]  The instance data which shall be sent to the other DICOM
+     *                          application; NULL, if there is none
+     *  @param commandSet [out] If this parameter is not NULL it will return a copy of the
+     *                          DIMSE command which is sent to the other DICOM application
+     *  @return EC_Normal if sending request was successful, an error code otherwise
+     */
+    OFCondition sendDIMSEMessage(const T_ASC_PresentationContextID presID,
+                                 T_DIMSE_Message* msg,
+                                 DcmDataset* dataObject,
+                                 DcmDataset** commandSet = NULL);
+
+    /** Returns SOP Class UID, SOP Instance UID and original transfer syntax for a given dataset.
+     *  If the dataset is NULL, all returned values will be undefined (i.e. empty or EXS_Unknown).
+     *  @param dataset        [in]  The dataset to read from
+     *  @param sopClassUID    [out] The value of attribute SOP Class UID if present
+     *  @param sopInstanceUID [out] The value of attribute SOP Instance UID if present
+     *  @param transferSyntax [out] The value of transfer syntax that originally was read from
+     *                              disk. Will be unknown if the dataset was created in memory.
+     *  @return EC_Normal if all information could be retrieved and is valid, an error code
+     *    otherwise
+     */
+    OFCondition getDatasetInfo(DcmDataset* dataset,
+                               OFString& sopClassUID,
+                               OFString& sopInstanceUID,
+                               E_TransferSyntax& transferSyntax);
+
+    /** Tells DcmSCU to use a secure TLS connection described by the given TLS layer
+     *  @param tlayer [in] The TLS transport layer including all TLS parameters
+     *  @return EC_Normal if given transport layer is ok, an error code otherwise
+     */
+    OFCondition useSecureConnection(DcmTransportLayer* tlayer);
+
+    /** Receive DIMSE command (excluding dataset!) over the currently open association
+     *  @param presID       [out] Contains in the end the ID of the presentation context
+     *                            which was specified in the DIMSE command received
+     *  @param msg          [out] The message received
+     *  @param statusDetail [out] If a non-NULL value is passed this variable will in the end
+     *                            contain detailed information with regard to the status
+     *                            information which is captured in the status element
+     *                            (0000,0900). Note that the value for element (0000,0900) is
+     *                            not contained in this return value but in internal msg. For
+     *                            details on the structure of this object, see DICOM standard
+     *                            part 7, annex C).
+     *  @param commandSet   [out] If this parameter is not NULL, it will return a copy of the
+     *                            DIMSE command which was received from the other DICOM
+     *                            application. The caller is responsible to de-allocate the
+     *                            returned object!
+     *  @param timeout      [in]  If this parameter is not 0, it specifies the timeout (in
+     *                            seconds) to be used for receiving the DIMSE command.
+     *                            Otherwise, the default timeout value is used (see
+     *                            setDIMSETimeout()).
+     *  @return EC_Normal if command could be received successfully, an error code otherwise
+     */
+    OFCondition receiveDIMSECommand(T_ASC_PresentationContextID* presID,
+                                    T_DIMSE_Message* msg,
+                                    DcmDataset** statusDetail,
+                                    DcmDataset** commandSet = NULL,
+                                    const Uint32 timeout    = 0);
+
+    /** Receives one dataset (of instance data) via network from another DICOM application
+     *  @param presID     [out] Contains in the end the ID of the presentation context which
+     *                          was used in the PDVs that were received on the network. If the
+     *                          PDVs show different presentation context IDs, this function
+     *                          will return an error.
+     *  @param dataObject [out] Contains in the end the information which was received over
+     *                          the network
+     *  @return EC_Normal if dataset could be received successfully, an error code otherwise
+     */
+    OFCondition receiveDIMSEDataset(T_ASC_PresentationContextID* presID, DcmDataset** dataObject);
 
-  /// DIMSE timeout (default: unlimited)
-  Uint32 m_dimseTimeout;
+    /** clear list of presentation contexts. In addition, any currently selected association
+     *  configuration file is disabled.
+     */
+    void clearPresentationContexts();
+
+    /** After negotiation association, this call returns the presentation context belonging
+     *  to the given presentation context ID
+     *  @param presID         [in]  The presentation context ID to look for
+     *  @param abstractSyntax [out] The abstract syntax (UID) for that ID.
+     *                              Empty, if such a presentation context does not exist.
+     *  @param transferSyntax [out] The transfer syntax (UID) for that ID.
+     *                              Empty, if such a presentation context does not exist.
+     */
+    void findPresentationContext(const T_ASC_PresentationContextID presID,
+                                 OFString& abstractSyntax,
+                                 OFString& transferSyntax);
+
+    /* ***********************************************************************
+     *  Functions particularly interesting for overwriting in derived classes
+     * *********************************************************************** */
+
+    /** This function is called if an object was received due to a C-GET request and can be
+     *  overwritten by a user in order to be informed about such an event. The default
+     *  implementation just prints a DEBUG message. Note that this function is not called if
+     *  the SCU is in storage mode DCMSCU_STORAGE_IGNORE.
+     *  @param filename       [in] The filename written
+     *  @param sopClassUID    [in] The SOP Class UID of the object written
+     *  @param sopInstanceUID [in] The SOP Instance UID of the object written
+     */
+    virtual void
+    notifyInstanceStored(const OFString& filename, const OFString& sopClassUID, const OFString& sopInstanceUID) const;
+
+    /** This function is called while sending DIMSE messages, i.e.\ on each PDV of a dataset.
+     *  The default implementation just prints a TRACE message on the number of bytes sent so
+     *  far. By overwriting this method, the progress of the send process can be shown to the
+     *  user in a more appropriate way. The progress notification can also be disabled
+     *  completely by calling setProgressNotificationMode().
+     *  @param byteCount [in] Number of bytes sent so far
+     */
+    virtual void notifySENDProgress(const unsigned long byteCount);
+
+    /** This function is called while receiving DIMSE messages, i.e.\ on each PDV of a dataset.
+     *  The default implementation just prints a TRACE message on the number of bytes received
+     *  so far. By overwriting this method, the progress of the receive process can be shown to
+     *  the user in a more appropriate way. The progress notification can also be disabled
+     *  completely by calling setProgressNotificationMode().
+     *  @param byteCount [in] Number of bytes received so far
+     */
+    virtual void notifyRECEIVEProgress(const unsigned long byteCount);
+
+    /** Check given N-EVENT-REPORT request and dataset for validity. This method is called by
+     *  handleEVENTREPORTRequest() before sending the response in order to determine the
+     *  DIMSE status code to be used for the response message.
+     *  @param request    [in] The N-EVENT-REPORT request message data structure
+     *  @param reqDataset [in] The N-EVENT-REPORT request dataset received. Might be NULL.
+     *  @return DIMSE status code to be used for the N-EVENT-REPORT response.
+     *          Always returns STATUS_Success (0). Derived classes should, therefore,
+     *          overwrite this method and return a more appropriate value based on the
+     *          result of the checks performed.
+     */
+    virtual Uint16 checkEVENTREPORTRequest(T_DIMSE_N_EventReportRQ& request, DcmDataset* reqDataset);
+
+    /** Sends back a C-STORE response on the given presentation context, with the designated
+     *  status, fitting the corresponding C-STORE request.
+     *  @param presID  [in] The presentation context ID to be used.
+     *  @param status  [in] The storage DIMSE status to be used.
+     *  @param request [in] The C-STORE request that should be responded to.
+     *  @result EC_Normal if the response could be sent, error otherwise.
+     */
+    virtual OFCondition
+    sendSTOREResponse(T_ASC_PresentationContextID presID, Uint16 status, const T_DIMSE_C_StoreRQ& request);
+
+    /** Helper function that generates a storage filename by extracting SOP Class and SOP
+     *  Instance UID from a dataset and combining that with the configured storage directory.
+     *  The SOP class is used to create an initial two letter abbreviation for the
+     *  corresponding modality, e.g. CT. An example for a storage filename created by this
+     *  function is "/storage_dir/CT.1.2.3.4.5" for a CT with SOP Instance UID "1.2.3.4.5".
+     *  This function might be overwritten to change the filename behaviour completely. This
+     *  function is only called if the SCU is in DCMSCU_STORAGE_DISK mode.
+     *  @param dataset [in] The dataset that should be stored to disk
+     *  @result Non-empty string if successful, otherwise empty string.
+     */
+    virtual OFString createStorageFilename(DcmDataset* dataset);
 
-  /// ACSE timeout (default: 30 seconds)
-  Uint32 m_acseTimeout;
+    /** Receives a DICOM dataset on a given presentation context ID but does not store it in
+     *  memory or disk, thus ignoring it.
+     *  @param presID  [in] The presentation context to be used
+     *  @param request [in] The corresponding C-STORE request
+     *  @return EC_Normal if ignoring worked, error code otherwise.
+     */
+    virtual OFCondition ignoreSTORERequest(T_ASC_PresentationContextID presID, const T_DIMSE_C_StoreRQ& request);
 
-  /// Storage directory for objects received with C-STORE due to a running
-  /// C-GET session. By default, the received objects are stored in the current
-  /// working directory.
-  OFString m_storageDir;
+    /* Callback functions (static) */
 
-  /// Set whether bit preserving storage should be enabled, i.e.\ any objects
-  /// retrieved via C-STORE should be written directly to disk without any data
-  /// correction/re-computation (e.g.\ group length calculations, padding, etc.).
-  /// This is especially interesting for retaining valid signatures, and also to
-  /// receive huge files which cannot be fully received in memory.
-  /// Default value: DCMSCU_STORAGE_DISK
-  DcmStorageMode m_storageMode;
+    /** Callback function used for sending DIMSE messages.
+     *  @param callbackContext [in] The desired user callback data
+     *  @param byteCount       [in] Progress bytes count
+     */
+    static void callbackSENDProgress(void* callbackContext, unsigned long byteCount);
 
-  /// Verbose PC mode (default: disabled)
-  OFBool m_verbosePCMode;
+    /** Callback function used for receiving DIMSE messages.
+     *  @param callbackContext [in] The desired user callback data
+     *  @param byteCount       [in] Progress bytes count
+     */
+    static void callbackRECEIVEProgress(void* callbackContext, unsigned long byteCount);
 
-  /// Dataset conversion mode (default: disabled)
-  OFBool m_datasetConversionMode;
+private:
+    /** Private undefined copy-constructor. Shall never be called.
+     *  @param src Source object
+     */
+    DcmSCU(const DcmSCU& src);
 
-  /// Progress notification mode (default: enabled)
-  OFBool m_progressNotificationMode;
+    /** Private undefined operator=. Shall never be called.
+     *  @param src Source object
+     *  @return Reference to this
+     */
+    DcmSCU& operator=(const DcmSCU& src);
+
+    /// Association of this SCU. This class only handles 1 association at a time.
+    T_ASC_Association* m_assoc;
+
+    /// The DICOM network the association is based on
+    T_ASC_Network* m_net;
+
+    /// Association parameters
+    T_ASC_Parameters* m_params;
 
-  /** Returns next available message ID free to be used by SCU
-   *  @return Next free message ID
-   */
-  Uint16 nextMessageID();
+    /// Configuration file for presentation contexts (optional)
+    OFString m_assocConfigFilename;
+
+    /// Profile in configuration file that should be used (optional)
+    OFString m_assocConfigProfile;
+
+    /// Defines presentation context, consisting of one abstract syntax name
+    /// and a list of transfer syntaxes for this abstract syntax
+    struct DCMTK_DCMNET_EXPORT DcmSCUPresContext
+    {
+        /** Default constructor
+         */
+        DcmSCUPresContext()
+            : abstractSyntaxName()
+            , transferSyntaxes()
+            , roleSelect(ASC_SC_ROLE_DEFAULT)
+        {
+        }
+        /// Abstract Syntax Name of Presentation Context
+        OFString abstractSyntaxName;
+        /// List of Transfer Syntaxes for Presentation Context
+        OFList<OFString> transferSyntaxes;
+        /// Role Selection
+        T_ASC_SC_ROLE roleSelect;
+    };
+
+    /// List of presentation contexts that should be negotiated
+    OFList<DcmSCUPresContext> m_presContexts;
+
+    /// Configuration file containing association parameters
+    OFString m_assocConfigFile;
+
+    /// The last DIMSE successfully sent, unresponded DIMSE request
+    T_DIMSE_Message* m_openDIMSERequest;
+
+    /// Maximum PDU size (default: 16384 bytes)
+    Uint32 m_maxReceivePDULength;
+
+    /// DIMSE blocking mode (default: blocking)
+    T_DIMSE_BlockingMode m_blockMode;
+
+    /// AE title of this application (default: ANY-SCU)
+    OFString m_ourAETitle;
+
+    /// Peer host (IP or host name)
+    OFString m_peer;
+
+    /// AE title of remote application (default: ANY-SCP)
+    OFString m_peerAETitle;
+
+    /// Port of remote application entity (default: 104)
+    Uint16 m_peerPort;
+
+    /// DIMSE timeout (default: unlimited)
+    Uint32 m_dimseTimeout;
+
+    /// ACSE timeout (default: 30 seconds)
+    Uint32 m_acseTimeout;
+
+    /// Storage directory for objects received with C-STORE due to a running
+    /// C-GET session. By default, the received objects are stored in the current
+    /// working directory.
+    OFString m_storageDir;
+
+    /// Set whether bit preserving storage should be enabled, i.e.\ any objects
+    /// retrieved via C-STORE should be written directly to disk without any data
+    /// correction/re-computation (e.g.\ group length calculations, padding, etc.).
+    /// This is especially interesting for retaining valid signatures, and also to
+    /// receive huge files which cannot be fully received in memory.
+    /// Default value: DCMSCU_STORAGE_DISK
+    DcmStorageMode m_storageMode;
+
+    /// Verbose PC mode (default: disabled)
+    OFBool m_verbosePCMode;
+
+    /// Dataset conversion mode (default: disabled)
+    OFBool m_datasetConversionMode;
+
+    /// Progress notification mode (default: enabled)
+    OFBool m_progressNotificationMode;
+
+    /** Returns next available message ID free to be used by SCU
+     *  @return Next free message ID
+     */
+    Uint16 nextMessageID();
 };
 
 #endif // SCU_H
index 3753df2b2efd643bc0529931d5ed27b92a0dd9ef..7400369e17a4bbab2952285423c9341f79104cb0 100644 (file)
@@ -1324,6 +1324,8 @@ dstorscp.o: dstorscp.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h ../include/dcmtk/dcmnet/scp.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
@@ -1349,8 +1351,6 @@ dstorscp.o: dstorscp.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
@@ -1437,12 +1437,12 @@ dstorscp.o: dstorscp.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofbmanip.h ../include/dcmtk/dcmnet/lst.h \
  ../include/dcmtk/dcmnet/dul.h ../include/dcmtk/dcmnet/extneg.h \
  ../include/dcmtk/dcmnet/dcuserid.h ../include/dcmtk/dcmnet/dntypes.h \
- ../include/dcmtk/dcmnet/dimse.h ../include/dcmtk/dcmnet/scpcfg.h \
- ../include/dcmtk/dcmnet/dcasccff.h ../include/dcmtk/dcmnet/dcasccfg.h \
- ../include/dcmtk/dcmnet/dccftsmp.h ../include/dcmtk/dcmnet/dccfuidh.h \
- ../include/dcmtk/dcmnet/dccfpcmp.h ../include/dcmtk/dcmnet/dccfrsmp.h \
- ../include/dcmtk/dcmnet/dccfenmp.h ../include/dcmtk/dcmnet/dccfprmp.h \
- ../include/dcmtk/dcmnet/diutil.h
+ ../include/dcmtk/dcmnet/dimse.h ../include/dcmtk/dcmnet/diutil.h \
+ ../include/dcmtk/dcmnet/scpcfg.h ../include/dcmtk/dcmnet/dcasccff.h \
+ ../include/dcmtk/dcmnet/dcasccfg.h ../include/dcmtk/dcmnet/dccftsmp.h \
+ ../include/dcmtk/dcmnet/dccfuidh.h ../include/dcmtk/dcmnet/dccfpcmp.h \
+ ../include/dcmtk/dcmnet/dccfrsmp.h ../include/dcmtk/dcmnet/dccfenmp.h \
+ ../include/dcmtk/dcmnet/dccfprmp.h
 dstorscu.o: dstorscu.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
@@ -1560,18 +1560,18 @@ dstorscu.o: dstorscu.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmnet/dcompat.h \
- ../../ofstd/include/dcmtk/ofstd/ofbmanip.h \
- ../include/dcmtk/dcmnet/dndefine.h ../include/dcmtk/dcmnet/dimse.h \
+ ../include/dcmtk/dcmnet/dcasccff.h ../include/dcmtk/dcmnet/dndefine.h \
+ ../include/dcmtk/dcmnet/dcasccfg.h ../include/dcmtk/dcmnet/assoc.h \
  ../include/dcmtk/dcmnet/dicom.h ../include/dcmtk/dcmnet/cond.h \
- ../../ofstd/include/dcmtk/ofstd/ofconsol.h ../include/dcmtk/dcmnet/lst.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../include/dcmtk/dcmnet/dcompat.h \
+ ../../ofstd/include/dcmtk/ofstd/ofbmanip.h ../include/dcmtk/dcmnet/lst.h \
  ../include/dcmtk/dcmnet/dul.h ../include/dcmtk/dcmnet/extneg.h \
  ../include/dcmtk/dcmnet/dcuserid.h ../include/dcmtk/dcmnet/dntypes.h \
- ../include/dcmtk/dcmnet/assoc.h ../include/dcmtk/dcmnet/dcasccff.h \
- ../include/dcmtk/dcmnet/dcasccfg.h ../include/dcmtk/dcmnet/dccftsmp.h \
- ../include/dcmtk/dcmnet/dccfuidh.h ../include/dcmtk/dcmnet/dccfpcmp.h \
- ../include/dcmtk/dcmnet/dccfrsmp.h ../include/dcmtk/dcmnet/dccfenmp.h \
- ../include/dcmtk/dcmnet/dccfprmp.h ../include/dcmtk/dcmnet/diutil.h
+ ../include/dcmtk/dcmnet/dccftsmp.h ../include/dcmtk/dcmnet/dccfuidh.h \
+ ../include/dcmtk/dcmnet/dccfpcmp.h ../include/dcmtk/dcmnet/dccfrsmp.h \
+ ../include/dcmtk/dcmnet/dccfenmp.h ../include/dcmtk/dcmnet/dccfprmp.h \
+ ../include/dcmtk/dcmnet/dimse.h ../include/dcmtk/dcmnet/diutil.h
 dul.o: dul.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmnet/diutil.h ../include/dcmtk/dcmnet/dicom.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
@@ -1974,21 +1974,26 @@ lst.o: lst.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../include/dcmtk/dcmnet/dndefine.h
 scp.o: scp.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmnet/scp.h ../../oflog/include/dcmtk/oflog/oflog.h \
- ../../oflog/include/dcmtk/oflog/logger.h \
- ../../oflog/include/dcmtk/oflog/config.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrmf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
  ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
@@ -2006,25 +2011,29 @@ scp.o: scp.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../include/dcmtk/dcmnet/assoc.h ../include/dcmtk/dcmnet/dicom.h \
+ ../include/dcmtk/dcmnet/cond.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../include/dcmtk/dcmnet/dndefine.h ../include/dcmtk/dcmnet/dcompat.h \
+ ../../ofstd/include/dcmtk/ofstd/ofbmanip.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../include/dcmtk/dcmnet/lst.h ../include/dcmtk/dcmnet/dul.h \
+ ../include/dcmtk/dcmnet/extneg.h ../include/dcmtk/dcmnet/dcuserid.h \
+ ../include/dcmtk/dcmnet/dntypes.h ../include/dcmtk/dcmnet/scp.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
@@ -2087,20 +2096,12 @@ scp.o: scp.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmnet/assoc.h ../include/dcmtk/dcmnet/dicom.h \
- ../include/dcmtk/dcmnet/cond.h \
- ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
- ../include/dcmtk/dcmnet/dndefine.h ../include/dcmtk/dcmnet/dcompat.h \
- ../../ofstd/include/dcmtk/ofstd/ofbmanip.h ../include/dcmtk/dcmnet/lst.h \
- ../include/dcmtk/dcmnet/dul.h ../include/dcmtk/dcmnet/extneg.h \
- ../include/dcmtk/dcmnet/dcuserid.h ../include/dcmtk/dcmnet/dntypes.h \
- ../include/dcmtk/dcmnet/dimse.h ../include/dcmtk/dcmnet/scpcfg.h \
- ../include/dcmtk/dcmnet/dcasccff.h ../include/dcmtk/dcmnet/dcasccfg.h \
- ../include/dcmtk/dcmnet/dccftsmp.h ../include/dcmtk/dcmnet/dccfuidh.h \
- ../include/dcmtk/dcmnet/dccfpcmp.h ../include/dcmtk/dcmnet/dccfrsmp.h \
- ../include/dcmtk/dcmnet/dccfenmp.h ../include/dcmtk/dcmnet/dccfprmp.h \
- ../include/dcmtk/dcmnet/diutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcostrmf.h
+ ../include/dcmtk/dcmnet/dimse.h ../include/dcmtk/dcmnet/diutil.h \
+ ../include/dcmtk/dcmnet/scpcfg.h ../include/dcmtk/dcmnet/dcasccff.h \
+ ../include/dcmtk/dcmnet/dcasccfg.h ../include/dcmtk/dcmnet/dccftsmp.h \
+ ../include/dcmtk/dcmnet/dccfuidh.h ../include/dcmtk/dcmnet/dccfpcmp.h \
+ ../include/dcmtk/dcmnet/dccfrsmp.h ../include/dcmtk/dcmnet/dccfenmp.h \
+ ../include/dcmtk/dcmnet/dccfprmp.h
 scpcfg.o: scpcfg.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmnet/scpcfg.h ../include/dcmtk/dcmnet/dcasccff.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
@@ -2182,6 +2183,8 @@ scppool.o: scppool.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../include/dcmtk/dcmnet/scpthrd.h ../include/dcmtk/dcmnet/scp.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
@@ -2207,8 +2210,6 @@ scppool.o: scppool.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
@@ -2294,14 +2295,16 @@ scppool.o: scppool.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofbmanip.h ../include/dcmtk/dcmnet/lst.h \
  ../include/dcmtk/dcmnet/dul.h ../include/dcmtk/dcmnet/extneg.h \
  ../include/dcmtk/dcmnet/dcuserid.h ../include/dcmtk/dcmnet/dntypes.h \
- ../include/dcmtk/dcmnet/dimse.h ../include/dcmtk/dcmnet/scpcfg.h \
- ../include/dcmtk/dcmnet/dcasccff.h ../include/dcmtk/dcmnet/dcasccfg.h \
- ../include/dcmtk/dcmnet/dccftsmp.h ../include/dcmtk/dcmnet/dccfuidh.h \
- ../include/dcmtk/dcmnet/dccfpcmp.h ../include/dcmtk/dcmnet/dccfrsmp.h \
- ../include/dcmtk/dcmnet/dccfenmp.h ../include/dcmtk/dcmnet/dccfprmp.h \
- ../include/dcmtk/dcmnet/diutil.h
+ ../include/dcmtk/dcmnet/dimse.h ../include/dcmtk/dcmnet/diutil.h \
+ ../include/dcmtk/dcmnet/scpcfg.h ../include/dcmtk/dcmnet/dcasccff.h \
+ ../include/dcmtk/dcmnet/dcasccfg.h ../include/dcmtk/dcmnet/dccftsmp.h \
+ ../include/dcmtk/dcmnet/dccfuidh.h ../include/dcmtk/dcmnet/dccfpcmp.h \
+ ../include/dcmtk/dcmnet/dccfrsmp.h ../include/dcmtk/dcmnet/dccfenmp.h \
+ ../include/dcmtk/dcmnet/dccfprmp.h
 scpthrd.o: scpthrd.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmnet/scpthrd.h ../include/dcmtk/dcmnet/scp.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
@@ -2334,8 +2337,6 @@ scpthrd.o: scpthrd.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
@@ -2422,30 +2423,33 @@ scpthrd.o: scpthrd.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofbmanip.h ../include/dcmtk/dcmnet/lst.h \
  ../include/dcmtk/dcmnet/dul.h ../include/dcmtk/dcmnet/extneg.h \
  ../include/dcmtk/dcmnet/dcuserid.h ../include/dcmtk/dcmnet/dntypes.h \
- ../include/dcmtk/dcmnet/dimse.h ../include/dcmtk/dcmnet/scpcfg.h \
- ../include/dcmtk/dcmnet/dcasccff.h ../include/dcmtk/dcmnet/dcasccfg.h \
- ../include/dcmtk/dcmnet/dccftsmp.h ../include/dcmtk/dcmnet/dccfuidh.h \
- ../include/dcmtk/dcmnet/dccfpcmp.h ../include/dcmtk/dcmnet/dccfrsmp.h \
- ../include/dcmtk/dcmnet/dccfenmp.h ../include/dcmtk/dcmnet/dccfprmp.h \
- ../include/dcmtk/dcmnet/diutil.h
+ ../include/dcmtk/dcmnet/dimse.h ../include/dcmtk/dcmnet/diutil.h \
+ ../include/dcmtk/dcmnet/scpcfg.h ../include/dcmtk/dcmnet/dcasccff.h \
+ ../include/dcmtk/dcmnet/dcasccfg.h ../include/dcmtk/dcmnet/dccftsmp.h \
+ ../include/dcmtk/dcmnet/dccfuidh.h ../include/dcmtk/dcmnet/dccfpcmp.h \
+ ../include/dcmtk/dcmnet/dccfrsmp.h ../include/dcmtk/dcmnet/dccfenmp.h \
+ ../include/dcmtk/dcmnet/dccfprmp.h
 scu.o: scu.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmnet/scu.h ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
- ../../oflog/include/dcmtk/oflog/oflog.h \
- ../../oflog/include/dcmtk/oflog/logger.h \
- ../../oflog/include/dcmtk/oflog/config.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrmf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
  ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
@@ -2464,36 +2468,43 @@ scu.o: scu.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../include/dcmtk/dcmnet/diutil.h ../include/dcmtk/dcmnet/dicom.h \
+ ../include/dcmtk/dcmnet/cond.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../include/dcmtk/dcmnet/dndefine.h ../include/dcmtk/dcmnet/dcompat.h \
+ ../../ofstd/include/dcmtk/ofstd/ofbmanip.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../include/dcmtk/dcmnet/dimse.h ../include/dcmtk/dcmnet/lst.h \
+ ../include/dcmtk/dcmnet/dul.h ../include/dcmtk/dcmnet/extneg.h \
+ ../include/dcmtk/dcmnet/dcuserid.h ../include/dcmtk/dcmnet/dntypes.h \
+ ../include/dcmtk/dcmnet/assoc.h ../include/dcmtk/dcmnet/scu.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
@@ -2542,16 +2553,7 @@ scu.o: scu.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../include/dcmtk/dcmnet/dcompat.h \
- ../../ofstd/include/dcmtk/ofstd/ofbmanip.h \
- ../include/dcmtk/dcmnet/dndefine.h ../include/dcmtk/dcmnet/dimse.h \
- ../include/dcmtk/dcmnet/dicom.h ../include/dcmtk/dcmnet/cond.h \
- ../../ofstd/include/dcmtk/ofstd/ofconsol.h ../include/dcmtk/dcmnet/lst.h \
- ../include/dcmtk/dcmnet/dul.h ../include/dcmtk/dcmnet/extneg.h \
- ../include/dcmtk/dcmnet/dcuserid.h ../include/dcmtk/dcmnet/dntypes.h \
- ../include/dcmtk/dcmnet/assoc.h ../include/dcmtk/dcmnet/dcasccff.h \
- ../include/dcmtk/dcmnet/dcasccfg.h ../include/dcmtk/dcmnet/dccftsmp.h \
- ../include/dcmtk/dcmnet/dccfuidh.h ../include/dcmtk/dcmnet/dccfpcmp.h \
- ../include/dcmtk/dcmnet/dccfrsmp.h ../include/dcmtk/dcmnet/dccfenmp.h \
- ../include/dcmtk/dcmnet/dccfprmp.h ../include/dcmtk/dcmnet/diutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcostrmf.h
+ ../include/dcmtk/dcmnet/dcasccff.h ../include/dcmtk/dcmnet/dcasccfg.h \
+ ../include/dcmtk/dcmnet/dccftsmp.h ../include/dcmtk/dcmnet/dccfuidh.h \
+ ../include/dcmtk/dcmnet/dccfpcmp.h ../include/dcmtk/dcmnet/dccfrsmp.h \
+ ../include/dcmtk/dcmnet/dccfenmp.h ../include/dcmtk/dcmnet/dccfprmp.h
index d5741a6910eb03df348c2a42bc1cdf012eccce0b..6dbe4ef4d36ad1d1820ae2c30e385adcefffb23d 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2018, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were partly developed by
@@ -286,12 +286,12 @@ ASC_createAssociationParameters(T_ASC_Parameters ** params,
     if (*params == NULL) return EC_MemoryExhausted;
     bzero((char*)*params, sizeof(**params));
 
-    strncpy((*params)->ourImplementationClassUID,
+    OFStandard::strlcpy((*params)->ourImplementationClassUID,
             OFFIS_IMPLEMENTATION_CLASS_UID,
-            sizeof((*params)->ourImplementationClassUID)-1);
-    strncpy((*params)->ourImplementationVersionName,
+            sizeof((*params)->ourImplementationClassUID));
+    OFStandard::strlcpy((*params)->ourImplementationVersionName,
             OFFIS_DTK_IMPLEMENTATION_VERSION_NAME,
-            sizeof((*params)->ourImplementationVersionName)-1);
+            sizeof((*params)->ourImplementationVersionName));
 
     if (strlen(OFFIS_DTK_IMPLEMENTATION_VERSION_NAME) > 16)
     {
@@ -303,9 +303,9 @@ ASC_createAssociationParameters(T_ASC_Parameters ** params,
     OFStandard::strlcpy((*params)->DULparams.callingImplementationVersionName,
         (*params)->ourImplementationVersionName, 16+1);
 
-    strncpy((*params)->DULparams.applicationContextName,
+    OFStandard::strlcpy((*params)->DULparams.applicationContextName,
             UID_StandardApplicationContext,
-            sizeof((*params)->DULparams.applicationContextName)-1);
+            sizeof((*params)->DULparams.applicationContextName));
 
     ASC_setAPTitles(*params,
                     "calling AP Title",
@@ -391,14 +391,14 @@ ASC_setAPTitles(T_ASC_Parameters * params,
                 const char* respondingAPTitle)
 {
     if (callingAPTitle)
-        strncpy(params->DULparams.callingAPTitle, callingAPTitle,
-                sizeof(params->DULparams.callingAPTitle)-1);
+        OFStandard::strlcpy(params->DULparams.callingAPTitle, callingAPTitle,
+                sizeof(params->DULparams.callingAPTitle));
     if (calledAPTitle)
-        strncpy(params->DULparams.calledAPTitle, calledAPTitle,
-                sizeof(params->DULparams.calledAPTitle)-1);
+        OFStandard::strlcpy(params->DULparams.calledAPTitle, calledAPTitle,
+                sizeof(params->DULparams.calledAPTitle));
     if (respondingAPTitle)
-        strncpy(params->DULparams.respondingAPTitle, respondingAPTitle,
-                sizeof(params->DULparams.respondingAPTitle)-1);
+        OFStandard::strlcpy(params->DULparams.respondingAPTitle, respondingAPTitle,
+                sizeof(params->DULparams.respondingAPTitle));
 
     return EC_Normal;
 }
@@ -440,13 +440,13 @@ ASC_setPresentationAddresses(T_ASC_Parameters * params,
                              const char* calledPresentationAddress)
 {
     if (callingPresentationAddress)
-        strncpy(params->DULparams.callingPresentationAddress,
+        OFStandard::strlcpy(params->DULparams.callingPresentationAddress,
                 callingPresentationAddress,
-                sizeof(params->DULparams.callingPresentationAddress)-1);
+                sizeof(params->DULparams.callingPresentationAddress));
     if (calledPresentationAddress)
-        strncpy(params->DULparams.calledPresentationAddress,
+        OFStandard::strlcpy(params->DULparams.calledPresentationAddress,
                 calledPresentationAddress,
-                sizeof(params->DULparams.calledPresentationAddress)-1);
+                sizeof(params->DULparams.calledPresentationAddress));
 
     return EC_Normal;
 }
@@ -1792,14 +1792,12 @@ ASC_receiveAssociation(T_ASC_Network * network,
     }
 
     // copy only maximum number of allowed characters
-    // trailing zero is always present because
-    // ASC_createAssociationParameters zero-initializes the complete struct.
-    strncpy(params->theirImplementationClassUID,
+    OFStandard::strlcpy(params->theirImplementationClassUID,
             params->DULparams.callingImplementationClassUID,
-            sizeof (params->theirImplementationClassUID) - 1);
-    strncpy(params->theirImplementationVersionName,
+            sizeof (params->theirImplementationClassUID));
+    OFStandard::strlcpy(params->theirImplementationVersionName,
             params->DULparams.callingImplementationVersionName,
-            sizeof (params->theirImplementationVersionName) - 1);
+            sizeof (params->theirImplementationVersionName));
 
     /*
      * The params->DULparams.peerMaxPDU parameter contains the
index 9a4305c59e7e13a820fcdb067b569d24e828b62a..8af0721a36b4ce9623895ff85223129caa62c9f3 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2018, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -77,10 +77,12 @@ DcmFindSCUDefaultCallback::DcmFindSCUDefaultCallback(
     DcmFindSCUExtractMode extractResponses,
     int cancelAfterNResponses,
     const char *outputDirectory,
-    STD_NAMESPACE ofstream *outputStream)
+    STD_NAMESPACE ofstream *outputStream,
+    const unsigned int limitOutput)
 : DcmFindSCUCallback()
 , extractResponses_(extractResponses)
 , cancelAfterNResponses_(cancelAfterNResponses)
+, limitOutput_(limitOutput)
 , outputDirectory_(OFSTRING_GUARD(outputDirectory))
 , outputStream_(outputStream)
 {
@@ -112,57 +114,70 @@ void DcmFindSCUDefaultCallback::callback(
     } else {
         DCMNET_INFO("Received Find Response " << responseCount << " (" << DU_cfindStatusString(rsp->DimseStatus) << ")");
     }
-
-    /* should we extract the response dataset to a DICOM file? */
-    if (extractResponses_ == FEM_dicomFile)
-    {
-        OFString outputFilename;
-        char rspIdsFileName[32];
-        sprintf(rspIdsFileName, "rsp%04d.dcm", responseCount);
-        OFStandard::combineDirAndFilename(outputFilename, outputDirectory_, rspIdsFileName, OFTrue /*allowEmptyDirName*/);
-        DCMNET_INFO("Writing response dataset to file: " << outputFilename);
-        DcmFindSCU::writeToFile(outputFilename.c_str(), responseIdentifiers);
-    }
-    /* ... or to an XML file? */
-    else if (extractResponses_ == FEM_xmlFile)
-    {
-        OFString outputFilename;
-        char rspIdsFileName[32];
-        sprintf(rspIdsFileName, "rsp%04d.xml", responseCount);
-        OFStandard::combineDirAndFilename(outputFilename, outputDirectory_, rspIdsFileName, OFTrue /*allowEmptyDirName*/);
-        DCMNET_INFO("Writing response dataset to file: " << outputFilename);
-        DcmFindSCU::writeToXMLFile(outputFilename.c_str(), responseIdentifiers);
-    }
-    /* ... or all responses to a single XML file? */
-    else if (extractResponses_ == FEM_singleXMLFile)
+    /* should we extract the response dataset to file? */
+    if (extractResponses_ != FEM_none)
     {
-        if (outputStream_ != NULL)
+        /* check for upper limit of extracted responses */
+        if ((limitOutput_ > 0) && (OFstatic_cast(unsigned int, responseCount) > limitOutput_))
         {
-            OFCondition cond = EC_Normal;
-            size_t writeFlags = 0;
-            DCMNET_DEBUG("Writing response dataset to XML file");
-            /* expect that (0008,0005) is set if extended characters are used */
-            if (responseIdentifiers->tagExistsWithValue(DCM_SpecificCharacterSet))
+            /* output warning message on first response after limit has been reached */
+            if (OFstatic_cast(unsigned int, responseCount) == limitOutput_ + 1)
+                DCMNET_INFO("Maximum number of responses already written to file ... not writing this and all following responses to file");
+            else
+                DCMNET_DEBUG("Maximum number of responses already written to file ... not writing this response to file");
+        } else {
+            /* should we extract the response dataset to a DICOM file? */
+            if (extractResponses_ == FEM_dicomFile)
+            {
+                OFString outputFilename;
+                char rspIdsFileName[32];
+                sprintf(rspIdsFileName, "rsp%04d.dcm", responseCount);
+                OFStandard::combineDirAndFilename(outputFilename, outputDirectory_, rspIdsFileName, OFTrue /*allowEmptyDirName*/);
+                DCMNET_INFO("Writing response dataset to file: " << outputFilename);
+                DcmFindSCU::writeToFile(outputFilename.c_str(), responseIdentifiers);
+            }
+            /* ... or to an XML file? */
+            else if (extractResponses_ == FEM_xmlFile)
+            {
+                OFString outputFilename;
+                char rspIdsFileName[32];
+                sprintf(rspIdsFileName, "rsp%04d.xml", responseCount);
+                OFStandard::combineDirAndFilename(outputFilename, outputDirectory_, rspIdsFileName, OFTrue /*allowEmptyDirName*/);
+                DCMNET_INFO("Writing response dataset to file: " << outputFilename);
+                DcmFindSCU::writeToXMLFile(outputFilename.c_str(), responseIdentifiers);
+            }
+            /* ... or all responses to a single XML file? */
+            else if (extractResponses_ == FEM_singleXMLFile)
             {
+                if (outputStream_ != NULL)
+                {
+                    OFCondition cond = EC_Normal;
+                    size_t writeFlags = 0;
+                    DCMNET_DEBUG("Writing response dataset to XML file");
+                    /* expect that (0008,0005) is set if extended characters are used */
+                    if (responseIdentifiers->tagExistsWithValue(DCM_SpecificCharacterSet))
+                    {
 #ifdef DCMTK_ENABLE_CHARSET_CONVERSION
-                DCMNET_DEBUG("Converting all element values that are affected by SpecificCharacterSet (0008,0005) to UTF-8");
-                cond = responseIdentifiers->convertToUTF8();
+                        DCMNET_DEBUG("Converting all element values that are affected by SpecificCharacterSet (0008,0005) to UTF-8");
+                        cond = responseIdentifiers->convertToUTF8();
 #else
-                if (responseIdentifiers->containsExtendedCharacters(OFFalse /*checkAllStrings*/))
-                {
-                    DCMNET_WARN("No support for character set conversion available ... quoting non-ASCII characters");
-                    /* make sure that non-ASCII characters are quoted appropriately */
-                    writeFlags |= DCMTypes::XF_convertNonASCII;
-                } else {
-                    DCMNET_DEBUG("No support for character set conversion available");
-                }
+                        if (responseIdentifiers->containsExtendedCharacters(OFFalse /*checkAllStrings*/))
+                        {
+                            DCMNET_WARN("No support for character set conversion available ... quoting non-ASCII characters");
+                            /* make sure that non-ASCII characters are quoted appropriately */
+                            writeFlags |= DCMTypes::XF_convertNonASCII;
+                        } else {
+                            DCMNET_DEBUG("No support for character set conversion available");
+                        }
 #endif
+                    }
+                    /* write response dataset to XML file */
+                    if (cond.good())
+                        cond = responseIdentifiers->writeXML(*outputStream_, writeFlags);
+                    if (cond.bad())
+                        DCMNET_ERROR("Writing XML file: " << cond.text());
+                }
             }
-            /* write response dataset to XML file */
-            if (cond.good())
-                cond = responseIdentifiers->writeXML(*outputStream_, writeFlags);
-            if (cond.bad())
-                DCMNET_ERROR("Writing XML file: " << cond.text());
         }
     }
 
@@ -184,7 +199,8 @@ void DcmFindSCUDefaultCallback::callback(
 
 
 DcmFindSCU::DcmFindSCU()
-: net_(NULL)
+: net_(NULL),
+  outputResponseLimit_(0)
 {
 }
 
@@ -193,6 +209,12 @@ DcmFindSCU::~DcmFindSCU()
     dropNetwork();
 }
 
+OFCondition DcmFindSCU::setOutputResponseLimit(const unsigned int limit)
+{
+    outputResponseLimit_ = limit;
+    return EC_Normal;
+}
+
 OFCondition DcmFindSCU::initializeNetwork(int acse_timeout)
 {
     return ASC_initializeNetwork(NET_REQUESTOR, 0, acse_timeout, &net_);
@@ -250,7 +272,11 @@ OFCondition DcmFindSCU::performQuery(
 
     /* initialize association parameters, i.e. create an instance of T_ASC_Parameters*. */
     OFCondition cond = ASC_createAssociationParameters(&params, maxReceivePDULength);
-    if (cond.bad()) return cond;
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Creating Association Parameters Failed: " << DimseCondition::dump(temp_str, cond));
+        return cond;
+    }
 
     /* sets this application's title and the called application's title in the params */
     /* structure. The default values to be set here are "FINDSCU" and "ANY-SCP". */
@@ -260,7 +286,12 @@ OFCondition DcmFindSCU::performQuery(
     /* structure. The default is an insecure connection; where OpenSSL is  */
     /* available the user is able to request an encrypted,secure connection. */
     cond = ASC_setTransportLayerType(params, secureConnection);
-    if (cond.bad()) return cond;
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Setting Transport Layer Type Failed: " << DimseCondition::dump(temp_str, cond));
+        (void) ASC_destroyAssociationParameters(&params);
+        return cond;
+    }
 
     /* Figure out the presentation addresses and copy the */
     /* corresponding values into the association parameters.*/
@@ -270,7 +301,12 @@ OFCondition DcmFindSCU::performQuery(
     /* Set the presentation contexts which will be negotiated */
     /* when the network connection will be established */
     cond = addPresentationContext(params, abstractSyntax, preferredTransferSyntax);
-    if (cond.bad()) return cond;
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Adding Presentation Contexts Failed: " << DimseCondition::dump(temp_str, cond));
+        (void) ASC_destroyAssociationParameters(&params);
+        return cond;
+    }
 
     /* dump presentation contexts if required */
     DCMNET_DEBUG("Request Parameters:" << OFendl << ASC_dumpParameters(temp_str, params, ASC_ASSOC_RQ));
@@ -283,14 +319,17 @@ OFCondition DcmFindSCU::performQuery(
 
     if (cond.bad())
     {
-        if (cond == DUL_ASSOCIATIONREJECTED) {
+        if (cond == DUL_ASSOCIATIONREJECTED)
+        {
             T_ASC_RejectParameters rej;
             ASC_getRejectParameters(params, &rej);
 
             DCMNET_ERROR("Association Rejected:" << OFendl << ASC_printRejectParameters(temp_str, &rej));
+            (void) ASC_destroyAssociation(&assoc); // this also destroys the T_ASC_Parameters structure
             return cond;
         } else {
             DCMNET_ERROR("Association Request Failed: " << DimseCondition::dump(temp_str, cond));
+            (void) ASC_destroyAssociation(&assoc); // this also destroys the T_ASC_Parameters structure
             return cond;
         }
     }
@@ -300,8 +339,10 @@ OFCondition DcmFindSCU::performQuery(
 
     /* count the presentation contexts which have been accepted by the SCP */
     /* If there are none, finish the execution */
-    if (ASC_countAcceptedPresentationContexts(params) == 0) {
+    if (ASC_countAcceptedPresentationContexts(params) == 0)
+    {
         DCMNET_ERROR("No Acceptable Presentation Contexts");
+        (void) ASC_destroyAssociation(&assoc); // this also destroys the T_ASC_Parameters structure
         return NET_EC_NoAcceptablePresentationContexts;
     }
 
@@ -362,6 +403,7 @@ OFCondition DcmFindSCU::performQuery(
             cond = ASC_abortAssociation(assoc);
             if (cond.bad()) {
                 DCMNET_ERROR("Association Abort Failed: " << DimseCondition::dump(temp_str, cond));
+                (void) ASC_destroyAssociation(&assoc); // this also destroys the T_ASC_Parameters structure
                 return cond;
             }
         } else {
@@ -371,6 +413,7 @@ OFCondition DcmFindSCU::performQuery(
             if (cond.bad())
             {
                 DCMNET_ERROR("Association Release Failed: " << DimseCondition::dump(temp_str, cond));
+                (void) ASC_destroyAssociation(&assoc); // this also destroys the T_ASC_Parameters structure
                 return cond;
             }
         }
@@ -382,20 +425,20 @@ OFCondition DcmFindSCU::performQuery(
         cond = ASC_abortAssociation(assoc);
         if (cond.bad()) {
             DCMNET_ERROR("Association Abort Failed: " << DimseCondition::dump(temp_str, cond));
+            (void) ASC_destroyAssociation(&assoc); // this also destroys the T_ASC_Parameters structure
             return cond;
         }
     }
     else if (cond == DUL_PEERABORTEDASSOCIATION)
     {
         DCMNET_INFO("Peer Aborted Association");
-    }
-    else
-    {
+    } else {
         DCMNET_ERROR("Find SCU Failed: " << DimseCondition::dump(temp_str, cond));
         DCMNET_INFO("Aborting Association");
         cond = ASC_abortAssociation(assoc);
         if (cond.bad()) {
             DCMNET_ERROR("Association Abort Failed: " << DimseCondition::dump(temp_str, cond));
+            (void) ASC_destroyAssociation(&assoc); // this also destroys the T_ASC_Parameters structure
             return cond;
         }
     }
@@ -404,7 +447,9 @@ OFCondition DcmFindSCU::performQuery(
     /* call is the counterpart of ASC_requestAssociation(...) which was called above. */
     cond = ASC_destroyAssociation(&assoc);
     if (cond.bad())
-        DCMNET_ERROR(DimseCondition::dump(temp_str, cond));
+    {
+        DCMNET_ERROR("Destroying Association Failed: " << DimseCondition::dump(temp_str, cond));
+    }
     return cond;
 }
 
@@ -648,7 +693,7 @@ OFCondition DcmFindSCU::findSCU(
         cond = proc.applyPathWithValue(dset, *path);
         if (cond.bad())
         {
-            DCMNET_ERROR("Bad override key/path: " << *path << ": " << cond.text());
+            DCMNET_ERROR("Bad override key/path: " << *path);
             return cond;
         }
         path++;
@@ -658,7 +703,7 @@ OFCondition DcmFindSCU::findSCU(
     presId = ASC_findAcceptedPresentationContextID(assoc, abstractSyntax);
 
     if (presId == 0) {
-        DCMNET_ERROR("No presentation context");
+        DCMNET_ERROR("No Presentation Context");
         return DIMSE_NOVALIDPRESENTATIONCONTEXTID;
     }
 
@@ -672,7 +717,7 @@ OFCondition DcmFindSCU::findSCU(
     req.Priority = DIMSE_PRIORITY_MEDIUM;
 
     /* prepare the callback data */
-    DcmFindSCUDefaultCallback defaultCallback(extractResponses, cancelAfterNResponses, outputDirectory, outputStream);
+    DcmFindSCUDefaultCallback defaultCallback(extractResponses, cancelAfterNResponses, outputDirectory, outputStream, outputResponseLimit_);
     if (callback == NULL) callback = &defaultCallback;
     callback->setAssociation(assoc);
     callback->setPresentationContextID(presId);
index 76e6ef9b661d1bd6479ef0afb59cc6aebcc7661f..8c647b63a3a831f02fc9d2bded1c66fad20ea8bc 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1993-2019, OFFIS e.V.
+ *  Copyright (C) 1993-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -66,339 +66,554 @@ static void DIMSE_dumpMessage_end(OFString &str, DcmItem *dataset = NULL)
     str += "======================= END DIMSE MESSAGE =======================";
 }
 
+static void DIMSE_printStatusClassString(STD_NAMESPACE ostream& dumpStream, int status)
+{
+  /* try to determine the Status Class of the DIMSE Status Code */
+  if (DICOM_SUCCESS_STATUS(status))
+    dumpStream << "Success";
+  else if (DICOM_FAILURE_STATUS(status))
+    dumpStream << "Failure";
+  else if (DICOM_WARNING_STATUS(status))
+    dumpStream << "Warning";
+  else if (DICOM_CANCEL_STATUS(status))
+    dumpStream << "Cancel";
+  else if (DICOM_PENDING_STATUS(status))
+    dumpStream << "Pending";
+  else if (DICOM_STANDARD_STATUS(status))
+    dumpStream << "Unknown Status Code";
+  else
+    dumpStream << "Unknown Status Code (non-standard)";
+}
+
 static void DIMSE_printNStatusString(STD_NAMESPACE ostream& dumpStream, int status)
 {
+  /* first, output the DIMSE status code in numeric format */
+  dumpStream << "0x" << STD_NAMESPACE hex << STD_NAMESPACE setfill('0')
+      << STD_NAMESPACE setw(4) << status << ": ";
+
   switch(status)
   {
-    case STATUS_Success:
-      dumpStream << "0x0000: Success";
+    /* General DIMSE-N Codes */
+    case STATUS_N_Success:
+      dumpStream << "Success";
+      break;
+    case STATUS_N_Refused_NotAuthorized:
+      dumpStream << "Refused: Not authorized";
       break;
     case STATUS_N_Cancel:
-      dumpStream << "0xFE00: Cancel";
+      dumpStream << "Cancel";
       break;
     case STATUS_N_AttributeListError:
-      dumpStream << "0x0107: Attribute list error";
+      dumpStream << "Attribute list error";
       break;
     case STATUS_N_SOPClassNotSupported:
-      dumpStream << "0x0122: SOP class not supported";
+      dumpStream << "SOP Class not supported";
       break;
     case STATUS_N_ClassInstanceConflict:
-      dumpStream << "0x0119: Class/instance conflict";
+      dumpStream << "Class-Instance conflict";
       break;
     case STATUS_N_DuplicateSOPInstance:
-      dumpStream << "0x0111: Duplicate SOP instance";
+      dumpStream << "Duplicate SOP Instance";
       break;
     case STATUS_N_DuplicateInvocation:
-      dumpStream << "0x0210: Duplicate invocation";
+      dumpStream << "Duplicate invocation";
       break;
     case STATUS_N_InvalidArgumentValue:
-      dumpStream << "0x0115: Invalid argument value";
+      dumpStream << "Invalid argument value";
       break;
     case STATUS_N_InvalidAttributeValue:
-      dumpStream << "0x0106: Invalid attribute value";
+      dumpStream << "Invalid attribute value";
       break;
     case STATUS_N_AttributeValueOutOfRange:
-      dumpStream << "0x0116: Attribute value out of range";
+      dumpStream << "Attribute value out of range";
       break;
-    case STATUS_N_InvalidObjectInstance:
-      dumpStream << "0x0117: Invalid object instance";
+    case STATUS_N_InvalidSOPInstance:
+      dumpStream << "Invalid SOP Instance";
       break;
     case STATUS_N_MissingAttribute:
-      dumpStream << "0x0120: Missing attribute";
+      dumpStream << "Missing attribute";
       break;
     case STATUS_N_MissingAttributeValue:
-      dumpStream << "0x0121: Missing attribute value";
+      dumpStream << "Missing attribute value";
       break;
     case STATUS_N_MistypedArgument:
-      dumpStream << "0x0212: Mistyped argument";
+      dumpStream << "Mistyped argument";
+      break;
+    case STATUS_N_NoSuchAction:
+      dumpStream << "No such action";
       break;
     case STATUS_N_NoSuchArgument:
-      dumpStream << "0x0114: No such argument";
+      dumpStream << "No such argument";
       break;
     case STATUS_N_NoSuchAttribute:
-      dumpStream << "0x0105: No such attribute";
+      dumpStream << "No such attribute";
       break;
     case STATUS_N_NoSuchEventType:
-      dumpStream << "0x0113: No such event type";
+      dumpStream << "No such Event Type";
       break;
-    case STATUS_N_NoSuchObjectInstance:
-      dumpStream << "0x0112: No such object instance";
+    case STATUS_N_NoSuchSOPInstance:
+      dumpStream << "No such SOP Instance";
       break;
     case STATUS_N_NoSuchSOPClass:
-      dumpStream << "0x0118: No such SOP class";
+      dumpStream << "No such SOP Class";
       break;
     case STATUS_N_ProcessingFailure:
-      dumpStream << "0x0110: Processing failure";
+      dumpStream << "Processing failure";
       break;
     case STATUS_N_ResourceLimitation:
-      dumpStream << "0x0213: Resource limitation";
+      dumpStream << "Resource limitation";
       break;
     case STATUS_N_UnrecognizedOperation:
-      dumpStream << "0x0211: Unrecognized operation";
+      dumpStream << "Unrecognized operation";
       break;
+
+    /* Print Management Service Class Specific Codes */
     case STATUS_N_PRINT_BFS_Warn_MemoryAllocation:
-      dumpStream << "0xB600: Basic film session warning - Memory allocation";
+      dumpStream << "Basic film session warning - Memory allocation";
       break;
     case STATUS_N_PRINT_BFS_Warn_NoSessionPrinting:
-      dumpStream << "0xB601: Basic film session warning - No session printing";
+      dumpStream << "Basic film session warning - No session printing";
       break;
     case STATUS_N_PRINT_BFS_Warn_EmptyPage:
-      dumpStream << "0xB602: Basic film session warning - Empty page";
+      dumpStream << "Basic film session warning - Empty page";
       break;
     case STATUS_N_PRINT_BFB_Warn_EmptyPage:
-      dumpStream << "0xB603: Basic film box warning - Empty page";
+      dumpStream << "Basic film box warning - Empty page";
+      break;
+    case STATUS_N_PRINT_BFS_BFB_IB_Warn_ImageDemagnified:
+      dumpStream << "Basic film session/box or image box warning - Image demagnified";
+      break;
+    case STATUS_N_PRINT_BFS_BFB_IB_Warn_ImageCropped:
+      dumpStream << "Basic film session/box or image box warning - Image cropped";
+      break;
+    case STATUS_N_PRINT_BFS_BFB_IB_Warn_ImageDecimated:
+      dumpStream << "Basic film session/box or image box warning - Image decimated";
       break;
     case STATUS_N_PRINT_BFS_Fail_NoFilmBox:
-      dumpStream << "0xC600: Basic film session failure - No film box";
+      dumpStream << "Basic film session failure - No film box";
       break;
     case STATUS_N_PRINT_BFS_Fail_PrintQueueFull:
-      dumpStream << "0xC601: Basic film session failure - Print queue full";
+      dumpStream << "Basic film session failure - Print queue full";
       break;
-    case STATUS_N_PRINT_BSB_Fail_PrintQueueFull:
-      dumpStream << "0xC602: Basic film box failure - Print queue full";
+    case STATUS_N_PRINT_BFB_Fail_PrintQueueFull:
+      dumpStream << "Basic film box failure - Print queue full";
       break;
     case STATUS_N_PRINT_BFS_BFB_Fail_ImageSize:
-      dumpStream << "0xC603: Basic film session/box failure - Image size";
+      dumpStream << "Basic film session/box failure - Image size";
+      break;
+    case STATUS_N_PRINT_BFS_BFB_Fail_PositionCollision:    // retired
+      dumpStream << "Basic film session/box failure - Position collision (retired)";
+      break;
+    case STATUS_N_PRINT_BFS_BFB_Fail_CombinedImageSize:
+      dumpStream << "Basic film session/box failure - Combined image size";
       break;
-    case STATUS_N_PRINT_BFS_BFB_Fail_PositionCollision:
-      dumpStream << "0xC604: Basic film session/box failure - Position collision";
+    case STATUS_N_PRINT_IB_Warn_MinMaxDensity:
+      dumpStream << "Image box warning - Min/Max density";
       break;
     case STATUS_N_PRINT_IB_Fail_InsufficientMemory:
-      dumpStream << "0xC605: Image box failure - Insufficient memory";
+      dumpStream << "Image box failure - Insufficient memory";
       break;
     case STATUS_N_PRINT_IB_Fail_MoreThanOneVOILUT:
-      dumpStream << "0xC606: Image box failure - More than one VOI LUT";
+      dumpStream << "Image box failure - More than one VOI LUT";
       break;
+
+    /* Modality Performed Procedure Step Retrieve SOP Class Specific Codes */
+    case STATUS_N_MPPS_Warning_RequestedOptionalAttributesNotSupported:
+      dumpStream << "MPPS retrieve warning: Requested optional attributes not supported";
+      break;
+
+    /* Application Event Logging Service Class Specific Codes */
+    case STATUS_N_LOG_Failure_ProceduralLoggingNotAvailable:
+      dumpStream << "Event logging failure - Procedural logging not available";
+      break;
+    case STATUS_N_LOG_Failure_EventInformationDoesNotMatchTemplate:
+      dumpStream << "Event logging failure - Event information does not match template";
+      break;
+    case STATUS_N_LOG_Failure_CannotMatchEventToCurrentStudy:
+      dumpStream << "Event logging failure - Cannot match event to a current study";
+      break;
+    case STATUS_N_LOG_Failure_IDsInconsistentInMatchingCurrentStudy:
+      dumpStream << "Event logging failure - IDs inconsistent in matching a current study - Event not logged";
+      break;
+    case STATUS_N_LOG_Warning_SynchronizationFrameOfReferenceDoesNotMatch:
+      dumpStream << "Event logging warning - Synchronization Frame of Reference does not match";
+      break;
+    case STATUS_N_LOG_Warning_StudyInstanceUIDCoercion:
+      dumpStream << "Event logging warning - Study Instance UID coercion";
+      break;
+    case STATUS_N_LOG_Warning_IDsInconsistentInMatchingCurrentStudy:
+      dumpStream << "Event logging warning - IDs inconsistent in matching a current study - Event logged";
+      break;
+
+    /* Media Creation Management Service Class Specific Codes */
+    case STATUS_N_MEDIA_Failed_MediaCreationActionAlreadyReceived:
+      dumpStream << "Media creation failure - Action already received";
+      break;
+    case STATUS_N_MEDIA_Failed_MediaCreationRequestAlreadyCompleted:
+      dumpStream << "Media creation failure - Request already completed";
+      break;
+    case STATUS_N_MEDIA_Failed_MediaCreationRequestAlreadyInProgress:
+      dumpStream << "Media creation failure - Request already in progress";
+      break;
+    case STATUS_N_MEDIA_Failed_CancellationDenied:
+      dumpStream << "Media creation failure - Cancellation denied";
+      break;
+
+    /* other codes (try to determine the Status Class) */
     default:
-      dumpStream << "0x" << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
-          << status << ": Unknown Status Code";
+      DIMSE_printStatusClassString(dumpStream, status);
       break;
   }
 }
 
 static void DIMSE_printCStoreStatusString(STD_NAMESPACE ostream& dumpStream, int status)
 {
+  /* first, output the DIMSE status code in numeric format */
   dumpStream << "0x" << STD_NAMESPACE hex << STD_NAMESPACE setfill('0')
-      << STD_NAMESPACE setw(4) << status;
+      << STD_NAMESPACE setw(4) << status << ": ";
 
-  if ((status & 0xff00) == STATUS_STORE_Refused_OutOfResources)
+  /* General C-STORE Codes */
+  if (status == STATUS_STORE_Success)
   {
-    dumpStream << ": Error: Refused - Out of resources";
+    dumpStream << "Success";
   }
   else if (status == STATUS_STORE_Refused_SOPClassNotSupported)
   {
-    dumpStream << ": Error: Refused - SOP Class not supported";
+    dumpStream << "Refused: SOP Class not supported";
   }
-  else if ((status & 0xff00) == STATUS_STORE_Error_DataSetDoesNotMatchSOPClass)
+  else if (status == STATUS_STORE_Refused_NotAuthorized)
   {
-    dumpStream << ": Error: Refused - Data Set does not match SOP Class";
+    dumpStream << "Refused: Not authorized";
   }
-  else if ((status & 0xf000) == STATUS_STORE_Error_CannotUnderstand)
+  else if (status == STATUS_STORE_InvalidSOPClass)
   {
-    dumpStream << ": Error: Cannot understand";
+    dumpStream << "Invalid SOP Class";
   }
-  else if (status == STATUS_STORE_Warning_CoercionOfDataElements)
+  else if (status == STATUS_STORE_DuplicateInvocation)
   {
-    dumpStream << ": Warning: Coercion of data elements";
+    dumpStream << "Duplicate invocation";
   }
-  else if (status == STATUS_STORE_Warning_DataSetDoesNotMatchSOPClass)
+  else if (status == STATUS_STORE_UnrecognizedOperation)
   {
-    dumpStream << ": Warning: Data Set does not match SOP Class";
+    dumpStream << "Unrecognized operation";
   }
-  else if (status == STATUS_STORE_Warning_ElementsDiscarded)
+  else if (status == STATUS_STORE_MistypedArgument)
   {
-    dumpStream << ": Warning: Elements discarded";
+    dumpStream << "Mistyped argument";
   }
-  else if (DICOM_WARNING_STATUS(status))
+
+  /* Service Class Specific C-STORE Codes */
+  else if ((status & 0xff00) == STATUS_STORE_Refused_OutOfResources)
   {
-    dumpStream << ": Warning";
+    dumpStream << "Refused: Out of resources";
   }
-  else if (DICOM_PENDING_STATUS(status))
+  else if ((status & 0xff00) == STATUS_STORE_Error_DataSetDoesNotMatchSOPClass)
+  {
+    dumpStream << "Error: Data Set does not match SOP Class";
+  }
+  else if ((status & 0xf000) == STATUS_STORE_Error_CannotUnderstand)
   {
-    dumpStream << ": Pending";
+    dumpStream << "Error: Cannot understand";
   }
-  else if (status == STATUS_Success)
+  else if (status == STATUS_STORE_Warning_CoercionOfDataElements)
+  {
+    dumpStream << "Warning: Coercion of Data Elements";
+  }
+  else if (status == STATUS_STORE_Warning_DataSetDoesNotMatchSOPClass)
   {
-    dumpStream << ": Success";
+    dumpStream << "Warning: Data Set does not match SOP Class";
   }
+  else if (status == STATUS_STORE_Warning_ElementsDiscarded)
+  {
+    dumpStream << "Warning: Elements discarded";
+  }
+
+  /* other codes (try to determine the Status Class) */
   else
   {
-    dumpStream << ": Unknown Status Code";
+    DIMSE_printStatusClassString(dumpStream, status);
   }
 }
 
-static void DIMSE_printCFindStatusString(STD_NAMESPACE ostream& dumpStream, int status)
+static void DIMSE_printCFindStatusString(STD_NAMESPACE ostream& dumpStream, int status, const char *sopClass)
 {
+  /* first, output the DIMSE status code in numeric format */
   dumpStream << "0x" << STD_NAMESPACE hex << STD_NAMESPACE setfill('0')
-      << STD_NAMESPACE setw(4) << status;
+      << STD_NAMESPACE setw(4) << status << ": ";
 
-  if ((status & 0xff00) == STATUS_FIND_Refused_OutOfResources)
+  /* General C-FIND Codes */
+  if (status == STATUS_FIND_Refused_SOPClassNotSupported)
   {
-    dumpStream << ": Error: Refused - Out of resources";
+    dumpStream << "Refused: SOP Class not supported";
   }
-  else if (status == STATUS_FIND_Refused_SOPClassNotSupported)
+
+  /* Service Class Specific C-FIND Codes */
+  else if (status == STATUS_FIND_Success_MatchingIsComplete)
   {
-    dumpStream << ": Error: Refused - SOP Class not supported";
+    dumpStream << "Success: Matching is complete";
   }
-  else if ((status & 0xff00) == STATUS_FIND_Failed_IdentifierDoesNotMatchSOPClass)
+  else if (status == STATUS_FIND_Refused_OutOfResources)
   {
-    dumpStream << ": Error: Failed - Identifier does not match SOP Class";
+    dumpStream << "Refused: Out of resources";
   }
-  else if ((status & 0xf000) == STATUS_FIND_Failed_UnableToProcess)
+  else if ((status & 0xff00) == STATUS_FIND_Error_DataSetDoesNotMatchSOPClass)
   {
-    dumpStream << ": Error: Failed - Unable to process";
+    dumpStream << "Error: Data Set does not match SOP Class";
   }
-  else if (status == STATUS_FIND_Cancel_MatchingTerminatedDueToCancelRequest)
-  {
-    dumpStream << ": Cancel: Matching terminated due to Cancel Request";
-  }
-  else if (status == STATUS_FIND_Pending_WarningUnsupportedOptionalKeys)
+  else if ((status & 0xf000) == STATUS_FIND_Failed_UnableToProcess)
   {
-    dumpStream << ": Pending: Warning - Unsupported optional keys";
+    /* Relevant Patient Information Query uses some specific Codes in "Cxxx" */
+    if (sopClass && (strncmp(sopClass, UID_RelevantPatientInformationQuery_Prefix, strlen(UID_RelevantPatientInformationQuery_Prefix)) == 0))
+    {
+      if (status == STATUS_FIND_Failed_MoreThanOneMatchFound)
+      {
+        dumpStream << "Failed: More than one match found";
+      }
+      else if (status == STATUS_FIND_Failed_UnableToSupportRequestedTemplate)
+      {
+        dumpStream << "Failed: Unable to support requested template";
+      }
+      else
+      {
+        dumpStream << "Failed: Unable to process";
+      }
+    }
+    /* for all other Services Classes, the generic output is used */
+    else
+    {
+      dumpStream << "Failed: Unable to process";
+    }
   }
-  else if (DICOM_WARNING_STATUS(status))
+  else if (status == STATUS_FIND_Cancel_MatchingTerminatedDueToCancelRequest)
   {
-    dumpStream << ": Warning";
+    dumpStream << "Cancel: Matching terminated due to Cancel Request";
   }
-  else if (DICOM_PENDING_STATUS(status))
+  else if (status == STATUS_FIND_Pending_MatchesAreContinuing)
   {
-    dumpStream << ": Pending";
+    dumpStream << "Pending: Matches are continuing";
   }
-  else if (status == STATUS_Success)
+  else if (status == STATUS_FIND_Pending_WarningUnsupportedOptionalKeys)
   {
-    dumpStream << ": Success";
+    dumpStream << "Pending: Matches are continuing - Warning: Unsupported optional keys";
   }
+
+  /* other codes (try to determine the Status Class) */
   else
   {
-    dumpStream << ": Unknown Status Code";
+    DIMSE_printStatusClassString(dumpStream, status);
   }
 }
 
 static void DIMSE_printCGetStatusString(STD_NAMESPACE ostream& dumpStream, int status)
 {
+  /* first, output the DIMSE status code in numeric format */
   dumpStream << "0x" << STD_NAMESPACE hex << STD_NAMESPACE setfill('0')
-      << STD_NAMESPACE setw(4) << status;
+      << STD_NAMESPACE setw(4) << status << ": ";
+
+  /* General C-GET Codes */
+  if (status == STATUS_GET_Refused_SOPClassNotSupported)
+  {
+    dumpStream << "Refused: SOP Class not supported";
+  }
+  else if (status == STATUS_GET_DuplicateInvocation)
+  {
+    dumpStream << "Duplicate invocation";
+  }
+  else if (status == STATUS_GET_UnrecognizedOperation)
+  {
+    dumpStream << "Unrecognized operation";
+  }
+  else if (status == STATUS_GET_MistypedArgument)
+  {
+    dumpStream << "Mistyped argument";
+  }
 
-  if ((status & 0xf000) == STATUS_GET_Failed_UnableToProcess)
+  /* Service Class Specific C-GET Codes */
+  else if (status == STATUS_GET_Success_SubOperationsCompleteNoFailures)
   {
-    dumpStream << ": Error: Failed - Unable to process";
+    dumpStream << "Success: Sub-operations complete - No failures or warnings";
   }
   else if (status == STATUS_GET_Refused_OutOfResourcesNumberOfMatches)
   {
-    dumpStream << ": Error: Refused - Out of resources - Number of matches";
+    dumpStream << "Refused: Out of resources - Unable to calculate number of matches";
   }
   else if (status == STATUS_GET_Refused_OutOfResourcesSubOperations)
   {
-    dumpStream << ": Error: Refused - Out of resources - Suboperations";
+    dumpStream << "Refused: Out of resources - Unable to perform sub-operations";
   }
-  else if (status == STATUS_GET_Failed_SOPClassNotSupported)
+  else if (status == STATUS_GET_Error_DataSetDoesNotMatchSOPClass)
   {
-    dumpStream << ": Failed: SOP Class not supported";
+    dumpStream << "Error: Data Set does not match SOP Class";
   }
-  else if (status == STATUS_GET_Failed_IdentifierDoesNotMatchSOPClass)
+  else if (status == STATUS_GET_Failed_NoneOfTheFramesWereFoundInSOPInstance)
   {
-    dumpStream << ": Failed: Identifier does not match SOP Class";
+    dumpStream << "Failed: None of the frames requested were found in SOP Instance";
   }
-  else if (status == STATUS_GET_Cancel_SubOperationsTerminatedDueToCancelIndication)
+  else if (status == STATUS_GET_Failed_UnableToCreateNewObjectForThisSOPClass)
   {
-    dumpStream << ": Cancel: Suboperations terminated due to Cancel Indication";
+    dumpStream << "Failed: Unable to create new object for this SOP Class";
   }
-  else if (status == STATUS_GET_Warning_SubOperationsCompleteOneOrMoreFailures)
+  else if (status == STATUS_GET_Failed_UnableToExtractFrames)
   {
-    dumpStream << ": Warning: Suboperations complete, one or more failures";
+    dumpStream << "Failed: Unable to extract frames";
   }
-  else if (DICOM_WARNING_STATUS(status))
+  else if (status == STATUS_GET_Failed_TimeBasedRequestForNonTimeBasedSOPInstance)
   {
-    dumpStream << ": Warning";
+    dumpStream << "Failed: Time-based request for non-time-based SOP Instance";
   }
-  else if (DICOM_PENDING_STATUS(status))
+  else if (status == STATUS_GET_Failed_InvalidRequest)
+  {
+    dumpStream << "Failed: Invalid request";
+  }
+  else if ((status & 0xf000) == STATUS_GET_Failed_UnableToProcess)
   {
-    dumpStream << ": Pending";
+    dumpStream << "Failed: Unable to process";
   }
-  else if (status == STATUS_Success)
+  else if (status == STATUS_GET_Cancel_SubOperationsTerminatedDueToCancelIndication)
   {
-    dumpStream << ": Success";
+    dumpStream << "Cancel: Sub-operations terminated due to Cancel Indication";
   }
+  else if (status == STATUS_GET_Warning_SubOperationsCompleteOneOrMoreFailures)
+  {
+    dumpStream << "Warning: Sub-operations complete - One or more failures or warnings";
+  }
+  else if (status == STATUS_GET_Pending_SubOperationsAreContinuing)
+  {
+    dumpStream << "Pending: Sub-operations are continuing";
+  }
+
+  /* other codes (try to determine the Status Class) */
   else
   {
-    dumpStream << ": Unknown Status Code";
+    DIMSE_printStatusClassString(dumpStream, status);
   }
 }
 
 static void DIMSE_printCMoveStatusString(STD_NAMESPACE ostream& dumpStream, int status)
 {
+  /* first, output the DIMSE status code in numeric format */
   dumpStream << "0x" << STD_NAMESPACE hex << STD_NAMESPACE setfill('0')
-      << STD_NAMESPACE setw(4) << status;
+      << STD_NAMESPACE setw(4) << status << ": ";
+
+  /* General C-MOVE Codes */
+  if (status == STATUS_MOVE_Refused_SOPClassNotSupported)
+  {
+    dumpStream << "Refused: SOP Class not supported";
+  }
+  else if (status == STATUS_MOVE_Refused_NotAuthorized)
+  {
+    dumpStream << "Refused: Not authorized";
+  }
+  else if (status == STATUS_MOVE_DuplicateInvocation)
+  {
+    dumpStream << "Duplicate invocation";
+  }
+  else if (status == STATUS_MOVE_UnrecognizedOperation)
+  {
+    dumpStream << "Unrecognized operation";
+  }
+  else if (status == STATUS_MOVE_MistypedArgument)
+  {
+    dumpStream << "Mistyped argument";
+  }
 
-  if ((status & 0xf000) == STATUS_MOVE_Failed_UnableToProcess)
+  /* Service Class Specific C-MOVE Codes */
+  else if (status == STATUS_MOVE_Success_SubOperationsCompleteNoFailures)
   {
-    dumpStream << ": Error: Failed - Unable to process";
+    dumpStream << "Success: Sub-operations complete - No failures or warnings";
   }
   else if (status == STATUS_MOVE_Refused_OutOfResourcesNumberOfMatches)
   {
-    dumpStream << ": Error: Refused - Out of resources - Number of matches";
+    dumpStream << "Refused: Out of resources - Unable to calculate number of matches";
   }
   else if (status == STATUS_MOVE_Refused_OutOfResourcesSubOperations)
   {
-    dumpStream << ": Error: Refused - Out of resources - Suboperations";
+    dumpStream << "Refused: Out of resources - Unable to perform sub-operations";
   }
-  else if (status == STATUS_MOVE_Failed_SOPClassNotSupported)
+  else if (status == STATUS_MOVE_Refused_MoveDestinationUnknown)
   {
-    dumpStream << ": Failed: SOP Class not supported";
+    dumpStream << "Refused: Move Destination unknown";
   }
-  else if (status == STATUS_MOVE_Failed_MoveDestinationUnknown)
+  else if (status == STATUS_MOVE_Error_DataSetDoesNotMatchSOPClass)
   {
-    dumpStream << ": Failed: Move Destination unknown";
+    dumpStream << "Error: Data Set does not match SOP Class";
   }
-  else if (status == STATUS_MOVE_Failed_IdentifierDoesNotMatchSOPClass)
+  else if (status == STATUS_MOVE_Failed_NoneOfTheFramesWereFoundInSOPInstance)
   {
-    dumpStream << ": Failed: Identifier does not match SOP Class";
+    dumpStream << "Failed: None of the frames requested were found in SOP Instance";
   }
-  else if (status == STATUS_MOVE_Cancel_SubOperationsTerminatedDueToCancelIndication)
+  else if (status == STATUS_MOVE_Failed_UnableToCreateNewObjectForThisSOPClass)
   {
-    dumpStream << ": Cancel: Suboperations terminated due to Cancel Indication";
+    dumpStream << "Failed: Unable to create new object for this SOP Class";
   }
-  else if (status == STATUS_MOVE_Warning_SubOperationsCompleteOneOrMoreFailures)
+  else if (status == STATUS_MOVE_Failed_UnableToExtractFrames)
   {
-    dumpStream << ": Warning: Suboperations complete, one or more failures";
+    dumpStream << "Failed: Unable to extract frames";
   }
-  else if (DICOM_WARNING_STATUS(status))
+  else if (status == STATUS_MOVE_Failed_TimeBasedRequestForNonTimeBasedSOPInstance)
   {
-    dumpStream << ": Warning";
+    dumpStream << "Failed: Time-based request for non-time-based SOP Instance";
   }
-  else if (DICOM_PENDING_STATUS(status))
+  else if (status == STATUS_MOVE_Failed_InvalidRequest)
   {
-    dumpStream << ": Pending";
+    dumpStream << "Failed: Invalid request";
   }
-  else if (status == STATUS_Success)
+  else if ((status & 0xf000) == STATUS_MOVE_Failed_UnableToProcess)
   {
-    dumpStream << ": Success";
+    dumpStream << "Failed: Unable to process";
   }
+  else if (status == STATUS_MOVE_Cancel_SubOperationsTerminatedDueToCancelIndication)
+  {
+    dumpStream << "Cancel: Sub-operations terminated due to Cancel Indication";
+  }
+  else if (status == STATUS_MOVE_Warning_SubOperationsCompleteOneOrMoreFailures)
+  {
+    dumpStream << "Warning: Sub-operations complete - One or more failures or warnings";
+  }
+  else if (status == STATUS_MOVE_Pending_SubOperationsAreContinuing)
+  {
+    dumpStream << "Pending: Sub-operations are continuing";
+  }
+
+  /* other codes (try to determine the Status Class) */
   else
   {
-    dumpStream << ": Unknown Status Code";
+    DIMSE_printStatusClassString(dumpStream, status);
   }
 }
 
 static void DIMSE_printCEchoStatusString(STD_NAMESPACE ostream& dumpStream, int status)
 {
+  /* first, output the DIMSE status code in numeric format */
   dumpStream << "0x" << STD_NAMESPACE hex << STD_NAMESPACE setfill('0')
-      << STD_NAMESPACE setw(4) << status;
-  if (DICOM_WARNING_STATUS(status))
+      << STD_NAMESPACE setw(4) << status << ": ";
+
+  /* General C-ECHO Codes */
+  if (status == STATUS_ECHO_Success)
   {
-    dumpStream << ": Warning";
+    dumpStream << "Success";
   }
-  else if (DICOM_PENDING_STATUS(status))
+  else if (status == STATUS_ECHO_Refused_SOPClassNotSupported)
   {
-    dumpStream << ": Pending";
+    dumpStream << "Refused: SOP Class not supported";
   }
-  else if (status == STATUS_Success)
+  else if (status == STATUS_ECHO_DuplicateInvocation)
   {
-    dumpStream << ": Success";
+    dumpStream << "Duplicate invocation";
   }
+  else if (status == STATUS_ECHO_UnrecognizedOperation)
+  {
+    dumpStream << "Unrecognized operation";
+  }
+  else if (status == STATUS_ECHO_MistypedArgument)
+  {
+    dumpStream << "Mistyped argument";
+  }
+
+  /* other codes (so try to determine the Status Class) */
   else
   {
-    dumpStream << ": Unknown Status Code";
+    DIMSE_printStatusClassString(dumpStream, status);
   }
 }
 
@@ -728,10 +943,10 @@ OFString& DIMSE_dumpMessage(OFString &str, T_DIMSE_C_FindRQ &msg, enum DIMSE_dir
 OFString& DIMSE_dumpMessage(OFString &str, T_DIMSE_C_FindRSP &msg, enum DIMSE_direction dir, DcmItem *dataset, T_ASC_PresentationContextID presID)
 {
     OFOStringStream stream;
-    const char *uid = NULL;
+    const char *sopClassUID = (msg.opts & O_FIND_AFFECTEDSOPCLASSUID) ? msg.AffectedSOPClassUID : NULL;
+    const char *sopClassName = dcmFindNameOfUID(sopClassUID);
 
     DIMSE_dumpMessage_start(str, dir);
-    if (msg.opts & O_FIND_AFFECTEDSOPCLASSUID) uid = dcmFindNameOfUID(msg.AffectedSOPClassUID);
     stream << "Message Type                  : C-FIND RSP" << OFendl;
     if (presID > 0)
     {
@@ -739,11 +954,15 @@ OFString& DIMSE_dumpMessage(OFString &str, T_DIMSE_C_FindRSP &msg, enum DIMSE_di
     }
     stream << "Message ID Being Responded To : " << msg.MessageIDBeingRespondedTo << OFendl
            << "Affected SOP Class UID        : ";
-    if (msg.opts & O_FIND_AFFECTEDSOPCLASSUID) stream << (uid ? uid : msg.AffectedSOPClassUID) << OFendl;
-    else stream << "none" << OFendl;
+    if (sopClassName)
+        stream << sopClassName << OFendl;
+    else if (sopClassUID)
+        stream << sopClassUID << OFendl;
+    else
+        stream << "none" << OFendl;
     stream << "Data Set                      : " << ((msg.DataSetType==DIMSE_DATASET_NULL) ? "none" : "present") << OFendl
            << "DIMSE Status                  : ";
-    DIMSE_printCFindStatusString(stream, msg.DimseStatus);
+    DIMSE_printCFindStatusString(stream, msg.DimseStatus, sopClassUID);
 
     OFSTRINGSTREAM_GETSTR(stream, result)
     str += result;
index 235dd378e656f95eae3ef156cea904c9450528e2..1fd98e2f7b4988917ed530b13ee1172ecc9cc0e8 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2018, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were partly developed by
@@ -144,7 +144,7 @@ DIMSE_findUser(
     T_DIMSE_Message req, rsp;
     DIC_US msgId;
     DcmDataset *rspIds = NULL;
-    DIC_US status = STATUS_Pending;
+    DIC_US status = STATUS_FIND_Pending_MatchesAreContinuing;
 
     /* if there is no search mask, nothing can be searched for */
     if (requestIdentifiers == NULL) return DIMSE_NULLKEY;
@@ -168,7 +168,7 @@ DIMSE_findUser(
     if (cond.bad()) return cond;
 
     /* try to receive (one or more) C-STORE-RSP messages, continue loop as long */
-    /* as no error occured and not all result information has been received. */
+    /* as no error occurred and not all result information has been received. */
     while (cond == EC_Normal && DICOM_PENDING_STATUS(status))
     {
        /* initialize the response to collect */
@@ -211,7 +211,7 @@ DIMSE_findUser(
 
         /* depending on the status which was returned in the current C-FIND-RSP, we need to do something */
         switch (status) {
-        case STATUS_Pending:
+        case STATUS_FIND_Pending_MatchesAreContinuing:
         case STATUS_FIND_Pending_WarningUnsupportedOptionalKeys:
             /* in these cases we received a C-FIND-RSP which indicates that a result data set was */
             /* found and will be sent over the network. We need to receive this result data set. */
@@ -243,7 +243,7 @@ DIMSE_findUser(
                     response, rspIds);
             }
             break;
-        case STATUS_Success:
+        case STATUS_FIND_Success:
             /* in this case the current C-FIND-RSP indicates that */
             /* there are no more records that match the search mask */
 
@@ -333,7 +333,7 @@ DIMSE_findProvider(
     /*
      * This function receives a data set which represents the search mask over the network and
      * stores this data in memory. Then, it tries to select corresponding records which match the
-     * search mask from some database (done whithin the callback function) and sends corresponding
+     * search mask from some database (done within the callback function) and sends corresponding
      * C-FIND-RSP messages to the other DICOM application this application is connected with.
      * The selection of each matching record and the sending of a corresponding C-FIND-RSP message
      * is conducted in a loop since there can be more than one search result. In the end, also the
@@ -362,7 +362,7 @@ DIMSE_findProvider(
     /* receive data (i.e. the search mask) and store it in memory */
     OFCondition cond = DIMSE_receiveDataSetInMemory(assoc, blockMode, timeout, &presIdData, &reqIds, NULL, NULL);
 
-    /* if no error occured while receiving data */
+    /* if no error occurred while receiving data */
     if (cond.good())
     {
         /* check if the presentation context IDs of the C-FIND-RQ and */
@@ -376,11 +376,11 @@ DIMSE_findProvider(
             /* if the IDs are the same go ahead */
             /* initialize the C-FIND-RSP message variable */
             bzero((char*)&rsp, sizeof(rsp));
-            rsp.DimseStatus = STATUS_Pending;
+            rsp.DimseStatus = STATUS_FIND_Pending_MatchesAreContinuing;
 
-            /* as long as no error occured and the status of the C-FIND-RSP message which will */
+            /* as long as no error occurred and the status of the C-FIND-RSP message which will */
             /* be/was sent is pending, perform this loop in which records that match the search */
-            /* mask are selected (whithin the execution of the callback function) and sent over */
+            /* mask are selected (within the execution of the callback function) and sent over */
             /* the network to the other DICOM application using C-FIND-RSP messages. */
             while (cond.good() && DICOM_PENDING_STATUS(rsp.DimseStatus) && normal)
             {
@@ -400,7 +400,7 @@ DIMSE_findProvider(
                 }
                 else
                 {
-                    /* some execption condition occured, bail out */
+                    /* some exception condition occurred, bail out */
                     normal = OFFalse;
                 }
 
index e3c2249504231abbbac41308f708f29908af9d49..f1375c698db1238126ee2829bbaa5ac4ace22fa5 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were partly developed by
@@ -100,7 +100,7 @@ DIMSE_getUser(
     DIC_US msgId;
     int responseCount = 0;
     T_ASC_Association *subAssoc = NULL;
-    DIC_US status = STATUS_Pending;
+    DIC_US status = STATUS_GET_Pending_SubOperationsAreContinuing;
 
     if (requestIdentifiers == NULL) return DIMSE_NULLKEY;
 
@@ -184,7 +184,7 @@ DIMSE_getUser(
         responseCount++;
 
         switch (status) {
-        case STATUS_Pending:
+        case STATUS_GET_Pending_SubOperationsAreContinuing:
             if (*statusDetail != NULL) {
                 DCMNET_WARN(DIMSE_warn_str(assoc) << "getUser: Pending with statusDetail, ignoring detail");
                 delete *statusDetail;
@@ -238,14 +238,14 @@ DIMSE_sendGetResponse(T_ASC_Association * assoc,
     rsp.msg.CGetRSP = *response;
     /* copy over stuff from request */
     rsp.msg.CGetRSP.MessageIDBeingRespondedTo = request->MessageID;
-    /* always send afected sop class uid */
+    /* always send affected sop class uid */
     OFStandard::strlcpy(rsp.msg.CGetRSP.AffectedSOPClassUID, request->AffectedSOPClassUID,
         sizeof(rsp.msg.CGetRSP.AffectedSOPClassUID));
     rsp.msg.CGetRSP.opts = O_GET_AFFECTEDSOPCLASSUID;
 
     switch (response->DimseStatus) {
-    case STATUS_Success:
-    case STATUS_Pending:
+    case STATUS_GET_Success:
+    case STATUS_GET_Pending_SubOperationsAreContinuing:
         /* Success cannot have a Failed SOP Instance UID list (no failures).
          * Pending may not send such a list.
          */
@@ -269,7 +269,7 @@ DIMSE_sendGetResponse(T_ASC_Association * assoc,
         O_GET_NUMBEROFWARNINGSUBOPERATIONS);
 
     switch (response->DimseStatus) {
-    case STATUS_Pending:
+    case STATUS_GET_Pending_SubOperationsAreContinuing:
     case STATUS_GET_Cancel_SubOperationsTerminatedDueToCancelIndication:
         break;
     default:
@@ -315,9 +315,9 @@ DIMSE_getProvider(
         else
         {
             bzero((char*)&rsp, sizeof(rsp));
-            rsp.DimseStatus = STATUS_Pending;   /* assume */
+            rsp.DimseStatus = STATUS_GET_Pending_SubOperationsAreContinuing;   /* assume */
 
-            while (cond == EC_Normal && rsp.DimseStatus == STATUS_Pending && normal)
+            while (cond == EC_Normal && rsp.DimseStatus == STATUS_GET_Pending_SubOperationsAreContinuing && normal)
             {
                 responseCount++;
 
@@ -330,7 +330,7 @@ DIMSE_getProvider(
                 } else if (cond == DIMSE_NODATAAVAILABLE) {
                     /* timeout */
                 } else {
-                    /* some execption condition occured, bail out */
+                    /* some exception condition occurred, bail out */
                     normal = OFFalse;
                 }
 
index e04a6a04f4fecea298568af6b45f617b09114ce2..01a4fb9e727a5c80be60642ad9a1ac41d882030a 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2018, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were partly developed by
@@ -165,7 +165,7 @@ DIMSE_moveUser(
     DIC_US msgId;
     int responseCount = 0;
     T_ASC_Association *subAssoc = NULL;
-    DIC_US status = STATUS_Pending;
+    DIC_US status = STATUS_MOVE_Pending_SubOperationsAreContinuing;
     OFBool firstLoop = OFTrue;
 
     if (requestIdentifiers == NULL) return DIMSE_NULLKEY;
@@ -187,7 +187,7 @@ DIMSE_moveUser(
     /* receive responses */
 
     OFTimer timer;
-    while (cond == EC_Normal && status == STATUS_Pending) {
+    while (cond == EC_Normal && status == STATUS_MOVE_Pending_SubOperationsAreContinuing) {
 
         /* if user wants, multiplex between net/subAssoc
          * and move responses over main assoc.
@@ -239,7 +239,7 @@ DIMSE_moveUser(
         responseCount++;
 
         switch (status) {
-        case STATUS_Pending:
+        case STATUS_MOVE_Pending_SubOperationsAreContinuing:
             if (*statusDetail != NULL) {
                 DCMNET_WARN(DIMSE_warn_str(assoc) << "moveUser: Pending with statusDetail, ignoring detail");
                 delete *statusDetail;
@@ -318,8 +318,8 @@ DIMSE_sendMoveResponse(
     rsp.msg.CMoveRSP.opts = O_MOVE_AFFECTEDSOPCLASSUID;
 
     switch (response->DimseStatus) {
-    case STATUS_Success:
-    case STATUS_Pending:
+    case STATUS_MOVE_Success:
+    case STATUS_MOVE_Pending_SubOperationsAreContinuing:
         /* Success cannot have a Failed SOP Instance UID list (no failures).
          * Pending may not send such a list.
          */
@@ -343,7 +343,7 @@ DIMSE_sendMoveResponse(
             O_MOVE_NUMBEROFWARNINGSUBOPERATIONS);
 
     switch (response->DimseStatus) {
-    case STATUS_Pending:
+    case STATUS_MOVE_Pending_SubOperationsAreContinuing:
     case STATUS_MOVE_Cancel_SubOperationsTerminatedDueToCancelIndication:
         break;
     default:
@@ -389,9 +389,9 @@ DIMSE_moveProvider(
           cond = makeDcmnetCondition(DIMSEC_INVALIDPRESENTATIONCONTEXTID, OF_error, "DIMSE: Presentation Contexts of Command and Data Differ");
         } else {
             bzero((char*)&rsp, sizeof(rsp));
-            rsp.DimseStatus = STATUS_Pending;   /* assume */
+            rsp.DimseStatus = STATUS_MOVE_Pending_SubOperationsAreContinuing;   /* assume */
 
-            while (cond == EC_Normal && rsp.DimseStatus == STATUS_Pending && normal) {
+            while (cond == EC_Normal && rsp.DimseStatus == STATUS_MOVE_Pending_SubOperationsAreContinuing && normal) {
                 responseCount++;
 
                 cond = DIMSE_checkForCancelRQ(assoc, presIdCmd, request->MessageID);
index 24189054d7fc252e54544e749d476d44ce51c7c4..5db5ea88835c098db1f7a6d2ffb72f68754ec443 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were partly developed by
@@ -406,7 +406,7 @@ DIMSE_storeProvider( T_ASC_Association *assoc,
 
     /* initialize the C-STORE-RSP message variable */
     bzero((char*)&response, sizeof(response));
-    response.DimseStatus = STATUS_Success;      /* assume */
+    response.DimseStatus = STATUS_STORE_Success;      /* assume */
     response.MessageIDBeingRespondedTo = request->MessageID;
     response.DataSetType = DIMSE_DATASET_NULL;  /* always for C-STORE-RSP */
     OFStandard::strlcpy(response.AffectedSOPClassUID, request->AffectedSOPClassUID, sizeof(response.AffectedSOPClassUID));
@@ -492,7 +492,7 @@ DIMSE_storeProvider( T_ASC_Association *assoc,
 
     /* depending on the error status, set the success indicating flag in the response message */
     if (cond == EC_Normal) {
-        response.DimseStatus = STATUS_Success;
+        response.DimseStatus = STATUS_STORE_Success;
     } else if (cond == DIMSE_OUTOFRESOURCES) {
         response.DimseStatus = STATUS_STORE_Refused_OutOfResources;
     } else {
index 526fe60fbbd661585f86cec84e36799896c37562..b8e9cc04443f0beae1df4e29c8e7792fb37c167a 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2019, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were partly developed by
@@ -1803,7 +1803,7 @@ receiveTransportConnectionTCP(PRIVATE_NETWORKKEY ** network,
         CloseHandle(hChildStdInWrite);
 
         // we need a STARTUPINFO and a PROCESS_INFORMATION structure for CreateProcess.
-        STARTUPINFO si;
+        STARTUPINFOA si;
         PROCESS_INFORMATION pi;
         memset(&pi,0,sizeof(pi));
         memset(&si,0,sizeof(si));
@@ -1818,7 +1818,7 @@ receiveTransportConnectionTCP(PRIVATE_NETWORKKEY ** network,
         si.hStdInput = hChildStdInRead;
 
         // create child process.
-        if (!CreateProcess(NULL,OFconst_cast(char *, cmdLine.c_str()), NULL, NULL, TRUE, 0, NULL, NULL, &si, &pi))
+        if (!CreateProcessA(NULL,OFconst_cast(char *, cmdLine.c_str()), NULL, NULL, TRUE, 0, NULL, NULL, &si, &pi))
         {
             OFOStringStream stream;
             stream << "Multi-Process Error: Creating process failed with error code "
index e3facda6482a504945ab760f8b6bc49a4f9f9ae4..91dcc7fcb910b7e607938829580a49af461cdf8f 100644 (file)
@@ -313,7 +313,7 @@ findSCUSCPRole(LST_HEAD ** lst, char *abstractSyntax);
 void destroyPresentationContextList(LST_HEAD ** l);
 void destroyUserInformationLists(DUL_USERINFO * userInfo);
 
-static FSM_Event_Description Event_Table[] = {
+static volatile FSM_Event_Description Event_Table[] = {
     {A_ASSOCIATE_REQ_LOCAL_USER, "A-ASSOCIATE request (local user)"},
     {TRANS_CONN_CONFIRM_LOCAL_USER, "Transport conn confirmation (local)"},
     {A_ASSOCIATE_AC_PDU_RCV, "A-ASSOCIATE-AC PDU (on transport)"},
@@ -335,7 +335,7 @@ static FSM_Event_Description Event_Table[] = {
     {INVALID_PDU, "Unrecognized/invalid PDU"}
 };
 
-static FSM_FUNCTION FSM_FunctionTable[] = {
+static volatile FSM_FUNCTION FSM_FunctionTable[] = {
     {AE_1, AE_1_TransportConnect, "AE 1 Transport Connect"},
     {AE_2, AE_2_SendAssociateRQPDU, "AE 2 Send Associate RQ PDU"},
     {AE_3, AE_3_AssociateConfirmationAccept, "AE 3 Associate Confirmation Accept"},
@@ -370,7 +370,7 @@ static FSM_FUNCTION FSM_FunctionTable[] = {
     {AR_10, AR_10_ConfirmRelease, "AR 10 Confirm Release"}
 };
 
-static FSM_ENTRY StateTable[DUL_NUMBER_OF_EVENTS][DUL_NUMBER_OF_STATES] = {
+static volatile FSM_ENTRY StateTable[DUL_NUMBER_OF_EVENTS][DUL_NUMBER_OF_STATES] = {
     {
         // EVENT,                    STATE,  ACTION,   NEXT_STATE
         {A_ASSOCIATE_REQ_LOCAL_USER, STATE1, AE_1, STATE4, "", "", NULL},
@@ -750,7 +750,7 @@ PRV_StateMachine(PRIVATE_NETWORKKEY ** network,
                  PRIVATE_ASSOCIATIONKEY ** association, int event, int state,
                  void *params)
 {
-    FSM_ENTRY
+    volatile FSM_ENTRY
         * entry;
 
     /* check if the given event is valid, if not return an error */
@@ -777,8 +777,8 @@ PRV_StateMachine(PRIVATE_NETWORKKEY ** network,
 
     /* dump information if required */
     DCMNET_TRACE("DUL  FSM Table: State: " << state << " Event: " << event << OFendl
-            << "DUL  Event:  " << entry->eventName << OFendl
-            << "DUL  Action: " << entry->actionName);
+            << "DUL  Event:  " << OFconst_cast(const char *, entry->eventName) << OFendl
+            << "DUL  Action: " << OFconst_cast(const char *, entry->actionName));
 
     /* if the state table's entry specifies an action function, execute this function and return */
     /* it's result value. If there is no action function defined, return a corresponding error. */
@@ -3476,7 +3476,7 @@ readPDUHeadTCP(PRIVATE_ASSOCIATIONKEY ** association,
 {
     unsigned long
         length;
-    static unsigned char
+    static const unsigned char
         legalPDUTypes[] = {
         DUL_TYPEASSOCIATERQ, DUL_TYPEASSOCIATEAC,
         DUL_TYPEASSOCIATERJ, DUL_TYPEDATA,
index 73185ad4fdf48737c67d89a26d8d84c685c2df4c..0a84f3850b9431b1e87558442e1a691a9658f7e0 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1994-2018, OFFIS e.V.
+ *  Copyright (C) 1994-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were partly developed by
@@ -607,9 +607,10 @@ parseUserInfo(DUL_USERINFO * userInfo,
 **      Parse the buffer and extract the Max PDU structure.
 **
 ** Parameter Dictionary:
-**      max             The structure to hold the Max PDU
-**      buf             The buffer that is to be parsed
-**      itemLength      Length of structure extracted.
+**      max             The structure to hold the Max PDU item
+**      buf             The buffer that is to be parsed (input/output value)
+**      itemLength      Length of structure extracted (output value)
+**      availData       Number of bytes announced to be available for this sub item (input value)
 **
 ** Return Values:
 **
@@ -636,6 +637,10 @@ parseMaxPDU(DUL_MAXLENGTH * max, unsigned char *buf,
     if (max->length != 4)
         DCMNET_WARN("Invalid length (" << max->length << ") for maximum length item, must be 4");
 
+    // Is there less data than the length field claims there is?
+    if (availData - 4 < max->length)
+        return makeLengthError("Max PDU", availData, 0, max->length);
+
     DCMNET_TRACE("Maximum PDU Length: " << (unsigned long)max->maxLength);
 
     return EC_Normal;
@@ -692,8 +697,9 @@ parseDummy(unsigned char *buf, unsigned long *itemLength, unsigned long availDat
 **
 ** Parameter Dictionary:
 **      role            The structure to hold the SCU-SCP role list
-**      buf             The buffer that is to be parsed
-**      itemLength      Length of structure extracted.
+**      buf             The buffer that is to be parsed (input/output value)
+**      itemLength      Length of structure extracted (output value)
+**      availData       Number of bytes announced to be available for this sub item (input value)
 **
 ** Return Values:
 **
@@ -733,10 +739,16 @@ parseSCUSCPRole(PRV_SCUSCPROLE * role, unsigned char *buf,
     if (UIDLength > DICOM_UI_LENGTH)
     {
       DCMNET_WARN("Provided role SOP Class UID length " << UIDLength
-      << " is larger than maximum allowed UID length " << DICOM_UI_LENGTH << " (will use 64 bytes max)");
+            << " is larger than maximum allowed UID length " << DICOM_UI_LENGTH << " (will use 64 bytes max)");
       UIDLength = DICOM_UI_LENGTH;
     }
-    OFStandard::strlcpy(role->SOPClassUID, (char*)buf, UIDLength+1 /* +1 for 0-byte */);
+
+    // The UID in the source buffer is not necessarily null terminated. Copy with memcpy
+    // and add a zero byte. We have already checked that there is enough data available
+    // in the source source buffer and enough space in the target buffer.
+    (void) memcpy(role->SOPClassUID, buf, UIDLength);
+    role->SOPClassUID[UIDLength] = '\0';
+
     buf += UIDLength;
     role->SCURole = *buf++;
     role->SCPRole = *buf++;
@@ -755,12 +767,18 @@ parseSCUSCPRole(PRV_SCUSCPROLE * role, unsigned char *buf,
 ** Purpose:
 **      Parse the buffer and extract the extended negotiation item
 **
+** Parameter Dictionary:
+**      extNeg          The structure to hold the extended negotiation item
+**      buf             The buffer that is to be parsed (input/output value)
+**      itemLength      Length of structure extracted (output value)
+**      availData       Number of bytes announced to be available for this sub item (input value)
+**
 ** Return Values:
 **
 */
 static OFCondition
 parseExtNeg(SOPClassExtendedNegotiationSubItem* extNeg, unsigned char *buf,
-                unsigned long *length, unsigned long availData)
+            unsigned long *length, unsigned long availData)
 {
     unsigned char *bufStart = buf;
 
@@ -825,8 +843,8 @@ parseExtNeg(SOPClassExtendedNegotiationSubItem* extNeg, unsigned char *buf,
  *
  * @param pdu The name of the field or PDU which got an invalid length field.
  * @param bufSize The size of the buffer that we received.
- * @param length The length as given by the length field.
  * @param minSize The minimum size that a 'pdu' has to have.
+ * @param length The length as given by the length field.
  */
 static OFCondition
 makeLengthError(const char *pdu, unsigned long bufSize, unsigned long minSize,
index e250de74e4a6b98c0832bacb41a0d390a4b174b9..e5f57a532e104ecffd41ab971ab63e9acad803cf 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2009-2018, OFFIS e.V.
+ *  Copyright (C) 2009-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 
 #include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 
-#include "dcmtk/dcmnet/scp.h"
-#include "dcmtk/dcmnet/assoc.h"
 #include "dcmtk/dcmdata/dcostrmf.h" /* for class DcmOutputFileStream */
+#include "dcmtk/dcmnet/assoc.h"
+#include "dcmtk/dcmnet/scp.h"
+#include "dcmtk/dcmtls/tlslayer.h"
 
 // ----------------------------------------------------------------------------
 
-DcmSCP::DcmSCP() :
-  m_assoc(NULL),
-  m_cfg()
+DcmSCP::DcmSCP()
+: m_network(NULL)
+, m_assoc(NULL)
+, m_cfg()
 {
-  OFStandard::initializeNetwork();
+    OFStandard::initializeNetwork();
 }
 
 // ----------------------------------------------------------------------------
 
 DcmSCP::~DcmSCP()
 {
-  // If there is an open association, drop it and free memory (just to be sure...)
-  if (m_assoc)
-  {
-    dropAndDestroyAssociation();
-  }
+    // If there is an open association, drop it and free memory (just to be sure...)
+    if (m_assoc)
+    {
+        dropAndDestroyAssociation();
+    }
+
+    // clean up network structure if initialized
+    if (m_network)
+    {
+        ASC_dropNetwork(&m_network);
+    }
 
-  OFStandard::shutdownNetwork();
+    OFStandard::shutdownNetwork();
 }
 
 // ----------------------------------------------------------------------------
 
 DcmSCPConfig& DcmSCP::getConfig()
 {
-  return *m_cfg;
+    return *m_cfg;
 }
 
 // ----------------------------------------------------------------------------
 
 OFCondition DcmSCP::setConfig(const DcmSCPConfig& config)
 {
-  if (isConnected())
-  {
-    return NET_EC_AlreadyConnected;
-  }
-  m_cfg = DcmSharedSCPConfig( config );
-  return EC_Normal;
+    if (isConnected())
+    {
+        return NET_EC_AlreadyConnected;
+    }
+    m_cfg = DcmSharedSCPConfig(config);
+    return EC_Normal;
 }
 
-
 // ----------------------------------------------------------------------------
 
-OFCondition DcmSCP::listen()
+OFCondition DcmSCP::openListenPort()
 {
-  // make sure not to let dcmdata remove trailing blank padding or perform other
-  // manipulations. We want to see the real data.
-  dcmEnableAutomaticInputDataCorrection.set( OFFalse );
 
-  OFCondition cond = EC_Normal;
-  // Make sure data dictionary is loaded.
-  if( !dcmDataDict.isDictionaryLoaded() )
-    DCMNET_WARN("No data dictionary loaded, check environment variable: " << DCM_DICT_ENVIRONMENT_VARIABLE);
+    // clean up network structure if already initialized
+    if (m_network)
+    {
+      ASC_dropNetwork(&m_network);
+      m_network = NULL;
+    }
+
+    // make sure not to let dcmdata remove trailing blank padding or perform other
+    // manipulations. We want to see the real data.
+    dcmEnableAutomaticInputDataCorrection.set(OFFalse);
+
+    OFCondition cond = EC_Normal;
+    // Make sure data dictionary is loaded.
+    if (!dcmDataDict.isDictionaryLoaded())
+        DCMNET_WARN("No data dictionary loaded, check environment variable: " << DCM_DICT_ENVIRONMENT_VARIABLE);
 
 #ifndef DISABLE_PORT_PERMISSION_CHECK
 #ifdef HAVE_GETEUID
-  // If port is privileged we must be as well.
-  if( m_cfg->getPort() < 1024 && geteuid() != 0 )
-  {
-    DCMNET_ERROR("No privileges to open this network port (" << m_cfg->getPort() << ")");
-    return NET_EC_InsufficientPortPrivileges;
-  }
+    // If port is privileged we must be as well.
+    if (m_cfg->getPort() < 1024 && geteuid() != 0)
+    {
+        DCMNET_ERROR("No privileges to open this network port (" << m_cfg->getPort() << ")");
+        return NET_EC_InsufficientPortPrivileges;
+    }
 #endif
 #endif
 
-  // Check whether current association profile is valid
-  OFString tmp;
-  OFCondition result = m_cfg->checkAssociationProfile(m_cfg->getActiveAssociationProfile(), tmp);
-  if (result.bad())
-    return result;
+    // Check whether current association profile is valid
+    OFString tmp;
+    OFCondition result = m_cfg->checkAssociationProfile(m_cfg->getActiveAssociationProfile(), tmp);
+    if (result.bad())
+        return result;
 
-  // Initialize network, i.e. create an instance of T_ASC_Network*.
-  T_ASC_Network *network = NULL;
-  cond = ASC_initializeNetwork( NET_ACCEPTOR, OFstatic_cast(int, m_cfg->getPort()), m_cfg->getACSETimeout(), &network );
-  if( cond.bad() )
-    return cond;
+    // Initialize network, i.e. create an instance of T_ASC_Network*.
+    cond = ASC_initializeNetwork(NET_ACCEPTOR, OFstatic_cast(int, m_cfg->getPort()), m_cfg->getACSETimeout(), &m_network);
+    if (cond.bad())
+    {
+        m_network = NULL;
+        return cond;
+    }
 
-  // drop root privileges now and revert to the calling user id (if we are running as setuid root)
-  cond = OFStandard::dropPrivileges();
-  if (cond.bad())
-  {
-      DCMNET_ERROR("setuid() failed, maximum number of processes/threads for uid already running.");
-      return cond;
-  }
-
-  // If we get to this point, the entire initialization process has been completed
-  // successfully. Now, we want to start handling all incoming requests. Since
-  // this activity is supposed to represent a server process, we do not want to
-  // terminate this activity (unless indicated by the stopAfterCurrentAssociation()
-  // or stopAfterConnectionTimeout() methods).
-  while( cond.good() )
-  {
-    // Wait for an association and handle the requests of
-    // the calling applications correspondingly.
-    cond = waitForAssociationRQ(network);
-
-    // Check whether we have a timeout
-    if (cond == DUL_NOASSOCIATIONREQUEST)
+    if (m_cfg->transportLayerEnabled())
     {
-      // If a stop is requested, stop
-      if (stopAfterConnectionTimeout())
-      {
-        cond = NET_EC_StopAfterConnectionTimeout;
-        break;
-      }
-      else
+      cond = ASC_setTransportLayer(m_network, m_cfg->getTransportLayer(), OFFalse /* Do not take over ownership */);
+      if (cond.bad())
       {
-        // stay in loop
-        cond = EC_Normal;
+          DCMNET_ERROR("DcmSCP: Error setting secure transport layer: " << cond.text());
+          return cond;
       }
     }
-    // Stop if SCP is told to stop after association was handled
-    else if (stopAfterCurrentAssociation())
+
+    // drop root privileges now and revert to the calling user id (if we are running as setuid root)
+    cond = OFStandard::dropPrivileges();
+    if (cond.bad())
+    {
+        DCMNET_ERROR("setuid() failed, maximum number of processes/threads for uid already running.");
+        return cond;
+    }
+
+    return cond;
+}
+
+// ----------------------------------------------------------------------------
+
+OFCondition DcmSCP::acceptAssociations()
+{
+    if (m_network == NULL)
+    {
+       DCMNET_ERROR("network port not initialized, call DcmSCP::openListenPort() first.");
+       return EC_IllegalCall;
+    }
+
+    OFCondition cond = EC_Normal;
+
+    // At this point, the entire initialization process has been completed
+    // successfully. Now, we want to start handling all incoming requests. Since
+    // this activity is supposed to represent a server process, we do not want to
+    // terminate this activity (unless indicated by the stopAfterCurrentAssociation()
+    // or stopAfterConnectionTimeout() methods).
+    while (cond.good())
     {
-      cond = NET_EC_StopAfterAssociation;
-      break;
+        // Wait for an association and handle the requests of
+        // the calling applications correspondingly.
+        cond = waitForAssociationRQ(m_network);
+
+        // Check whether we have a timeout
+        if (cond == DUL_NOASSOCIATIONREQUEST)
+        {
+            // If a stop is requested, stop
+            if (stopAfterConnectionTimeout())
+            {
+                cond = NET_EC_StopAfterConnectionTimeout;
+                break;
+            }
+            else
+            {
+                // stay in loop
+                cond = EC_Normal;
+            }
+        }
+        // Stop if SCP is told to stop after association was handled
+        else if (stopAfterCurrentAssociation())
+        {
+            cond = NET_EC_StopAfterAssociation;
+            break;
+        }
     }
-  }
 
-  // Drop the network, i.e. free memory of T_ASC_Network* structure. This call
-  // is the counterpart of ASC_initializeNetwork(...) which was called above.
-  ASC_dropNetwork( &network );
-  network = NULL;
+    // Drop the network, i.e. free memory of T_ASC_Network* structure. This call
+    // is the counterpart of ASC_initializeNetwork(...) which was called above.
+    ASC_dropNetwork(&m_network);
+    m_network = NULL;
+
+    // return ok
+    return cond;
+}
+
+// ----------------------------------------------------------------------------
 
-  // return ok
+OFCondition DcmSCP::listen()
+{
+  OFCondition cond = openListenPort();
+  if (cond.good()) cond = acceptAssociations();
   return cond;
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::findPresentationContext(const T_ASC_PresentationContextID presID,
-                                     OFString &abstractSyntax,
-                                     OFString &transferSyntax)
-{
-  transferSyntax.clear();
-  abstractSyntax.clear();
-  if (m_assoc == NULL)
-    return;
-
-  DUL_PRESENTATIONCONTEXT *pc;
-  LST_HEAD **l;
-
-  /* we look for a presentation context matching
-   * both abstract and transfer syntax
-   */
-  l = &m_assoc->params->DULparams.acceptedPresentationContext;
-  pc = (DUL_PRESENTATIONCONTEXT*) LST_Head(l);
-  (void)LST_Position(l, (LST_NODE*)pc);
-  while (pc)
-  {
-     if (presID == pc->presentationContextID)
-     {
-       if (pc->result == ASC_P_ACCEPTANCE)
-       {
-         // found a match
-         transferSyntax = pc->acceptedTransferSyntax;
-         abstractSyntax = pc->abstractSyntax;
-       }
-       break;
-     }
-     pc = (DUL_PRESENTATIONCONTEXT*) LST_Next(l);
-  }
-}
-
-
-DUL_PRESENTATIONCONTEXT* DcmSCP::findPresentationContextID(LST_HEAD *head,
+                                     OFString& abstractSyntax,
+                                     OFString& transferSyntax)
+{
+    transferSyntax.clear();
+    abstractSyntax.clear();
+    if (m_assoc == NULL)
+        return;
+
+    DUL_PRESENTATIONCONTEXT* pc;
+    LST_HEAD** l;
+
+    /* we look for a presentation context matching
+     * both abstract and transfer syntax
+     */
+    l  = &m_assoc->params->DULparams.acceptedPresentationContext;
+    pc = (DUL_PRESENTATIONCONTEXT*)LST_Head(l);
+    (void)LST_Position(l, (LST_NODE*)pc);
+    while (pc)
+    {
+        if (presID == pc->presentationContextID)
+        {
+            if (pc->result == ASC_P_ACCEPTANCE)
+            {
+                // found a match
+                transferSyntax = pc->acceptedTransferSyntax;
+                abstractSyntax = pc->abstractSyntax;
+            }
+            break;
+        }
+        pc = (DUL_PRESENTATIONCONTEXT*)LST_Next(l);
+    }
+}
+
+DUL_PRESENTATIONCONTEXT* DcmSCP::findPresentationContextID(LST_HEAD* head,
                                                            T_ASC_PresentationContextID presentationContextID)
 {
-  DUL_PRESENTATIONCONTEXT *pc;
-  LST_HEAD **l;
-  OFBool found = OFFalse;
+    DUL_PRESENTATIONCONTEXT* pc;
+    LST_HEAD** l;
+    OFBool found = OFFalse;
 
-  if (head == NULL)
-    return NULL;
+    if (head == NULL)
+        return NULL;
 
-  l = &head;
-  if (*l == NULL)
-    return NULL;
+    l = &head;
+    if (*l == NULL)
+        return NULL;
 
-  pc = (DUL_PRESENTATIONCONTEXT*) LST_Head(l);
-  (void)LST_Position(l, (LST_NODE*)pc);
+    pc = (DUL_PRESENTATIONCONTEXT*)LST_Head(l);
+    (void)LST_Position(l, (LST_NODE*)pc);
 
-  while (pc && !found)
-  {
-    if (pc->presentationContextID == presentationContextID)
-    {
-      found = OFTrue;
-    } else
+    while (pc && !found)
     {
-      pc = (DUL_PRESENTATIONCONTEXT*) LST_Next(l);
+        if (pc->presentationContextID == presentationContextID)
+        {
+            found = OFTrue;
+        }
+        else
+        {
+            pc = (DUL_PRESENTATIONCONTEXT*)LST_Next(l);
+        }
     }
-  }
-  return pc;
+    return pc;
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::refuseAssociation(const DcmRefuseReasonType reason)
 {
-  if (m_assoc == NULL)
-  {
-    DCMNET_WARN("DcmSCP::refuseAssociation() called but actually no association running, ignoring");
-    return;
-  }
-
-  T_ASC_RejectParameters rej;
-
-  // dump some information if required
-  switch( reason )
-  {
-    case DCMSCP_TOO_MANY_ASSOCIATIONS:
-      DCMNET_INFO("Refusing Association (too many associations)");
-      break;
-    case DCMSCP_CANNOT_FORK:
-      DCMNET_INFO("Refusing Association (cannot fork)");
-      break;
-    case DCMSCP_BAD_APPLICATION_CONTEXT_NAME:
-      DCMNET_INFO("Refusing Association (bad application context)");
-      break;
-    case DCMSCP_CALLING_HOST_NOT_ALLOWED:
-      DCMNET_INFO("Refusing Association (connecting host not allowed)");
-      break;
-    case DCMSCP_CALLED_AE_TITLE_NOT_RECOGNIZED:
-      DCMNET_INFO("Refusing Association (called AE title not recognized)");
-      break;
-    case DCMSCP_CALLING_AE_TITLE_NOT_RECOGNIZED:
-      DCMNET_INFO("Refusing Association (calling AE title not recognized)");
-      break;
-    case DCMSCP_FORCED:
-      DCMNET_INFO("Refusing Association (forced via command line)");
-      break;
-    case DCMSCP_NO_IMPLEMENTATION_CLASS_UID:
-      DCMNET_INFO("Refusing Association (no implementation class UID provided)");
-      break;
-    case DCMSCP_NO_PRESENTATION_CONTEXTS:
-      DCMNET_INFO("Refusing Association (no acceptable presentation contexts)");
-      break;
-    case DCMSCP_INTERNAL_ERROR:
-      DCMNET_INFO("Refusing Association (internal error)");
-      break;
-    default:
-      DCMNET_INFO("Refusing Association (unknown reason)");
-      break;
-  }
-
-  // Set some values in the reject message depending on the reason
-  switch( reason )
-  {
-    case DCMSCP_TOO_MANY_ASSOCIATIONS:
-      rej.result = ASC_RESULT_REJECTEDTRANSIENT;
-      rej.source = ASC_SOURCE_SERVICEPROVIDER_PRESENTATION_RELATED;
-      rej.reason = ASC_REASON_SP_PRES_LOCALLIMITEXCEEDED;
-      break;
-    case DCMSCP_CANNOT_FORK:
-      rej.result = ASC_RESULT_REJECTEDPERMANENT;
-      rej.source = ASC_SOURCE_SERVICEPROVIDER_PRESENTATION_RELATED;
-      rej.reason = ASC_REASON_SP_PRES_TEMPORARYCONGESTION;
-      break;
-    case DCMSCP_BAD_APPLICATION_CONTEXT_NAME:
-      rej.result = ASC_RESULT_REJECTEDTRANSIENT;
-      rej.source = ASC_SOURCE_SERVICEUSER;
-      rej.reason = ASC_REASON_SU_APPCONTEXTNAMENOTSUPPORTED;
-      break;
-    case DCMSCP_CALLED_AE_TITLE_NOT_RECOGNIZED:
-      rej.result = ASC_RESULT_REJECTEDPERMANENT;
-      rej.source = ASC_SOURCE_SERVICEUSER;
-      rej.reason = ASC_REASON_SU_CALLEDAETITLENOTRECOGNIZED;
-      break;
-    case DCMSCP_CALLING_AE_TITLE_NOT_RECOGNIZED:
-      rej.result = ASC_RESULT_REJECTEDPERMANENT;
-      rej.source = ASC_SOURCE_SERVICEUSER;
-      rej.reason = ASC_REASON_SU_CALLINGAETITLENOTRECOGNIZED;
-      break;
-    case DCMSCP_FORCED:
-    case DCMSCP_NO_IMPLEMENTATION_CLASS_UID:
-    case DCMSCP_NO_PRESENTATION_CONTEXTS:
-    case DCMSCP_CALLING_HOST_NOT_ALLOWED:
-    case DCMSCP_INTERNAL_ERROR:
-    default:
-      rej.result = ASC_RESULT_REJECTEDPERMANENT;
-      rej.source = ASC_SOURCE_SERVICEUSER;
-      rej.reason = ASC_REASON_SU_NOREASON;
-      break;
-  }
-
-  // Reject the association request.
-  ASC_rejectAssociation( m_assoc, &rej );
-}
-
-// ----------------------------------------------------------------------------
-
-OFCondition DcmSCP::waitForAssociationRQ(T_ASC_Network *network)
-{
-  if (network == NULL)
-    return ASC_NULLKEY;
-  if (m_assoc != NULL)
-    return DIMSE_ILLEGALASSOCIATION;
-
-  Uint32 timeout = m_cfg->getConnectionTimeout();
-
-  // Listen to a socket for timeout seconds and wait for an association request
-  OFCondition cond = ASC_receiveAssociation( network, &m_assoc, m_cfg->getMaxReceivePDULength(), NULL, NULL, OFFalse,
-                                             m_cfg->getConnectionBlockingMode(), OFstatic_cast(int, timeout) );
-
-  // In case of a timeout in non-blocking mode, call notifier (and return
-  // to main event loop later)
-  if ( cond == DUL_NOASSOCIATIONREQUEST )
-  {
-    notifyConnectionTimeout();
-  }
-  else
-  {
-    // If association could be received, handle it
-    if( cond.good() )
-    {
-      cond = processAssociationRQ();
-      // There was an association which has ended now:
-      // Call notifier and output separator line.
-      notifyAssociationTermination();
-      DCMNET_DEBUG( "+++++++++++++++++++++++++++++" );
-    }
-    // Else, if we could not receive an association request since there was
-    // some error, just ignore it (and continue in main event loop later)
-    else
+    if (m_assoc == NULL)
     {
-      DCMNET_ERROR("Could not receive association request: " << cond.text());
-      cond = EC_Normal;
+        DCMNET_WARN("DcmSCP::refuseAssociation() called but actually no association running, ignoring");
+        return;
     }
-  }
 
-  // We are done with this association, free it and set to NULL.
-  // ASC_receiveAssociation will always create a related structure, even
-  // if no association was received at all.
-  dropAndDestroyAssociation();
-  return cond;
+    T_ASC_RejectParameters rej;
+
+    // dump some information if required
+    switch (reason)
+    {
+        case DCMSCP_TOO_MANY_ASSOCIATIONS:
+            DCMNET_INFO("Refusing Association (too many associations)");
+            break;
+        case DCMSCP_CANNOT_FORK:
+            DCMNET_INFO("Refusing Association (cannot fork)");
+            break;
+        case DCMSCP_BAD_APPLICATION_CONTEXT_NAME:
+            DCMNET_INFO("Refusing Association (bad application context)");
+            break;
+        case DCMSCP_CALLING_HOST_NOT_ALLOWED:
+            DCMNET_INFO("Refusing Association (connecting host not allowed)");
+            break;
+        case DCMSCP_CALLED_AE_TITLE_NOT_RECOGNIZED:
+            DCMNET_INFO("Refusing Association (called AE title not recognized)");
+            break;
+        case DCMSCP_CALLING_AE_TITLE_NOT_RECOGNIZED:
+            DCMNET_INFO("Refusing Association (calling AE title not recognized)");
+            break;
+        case DCMSCP_FORCED:
+            DCMNET_INFO("Refusing Association (forced via command line)");
+            break;
+        case DCMSCP_NO_IMPLEMENTATION_CLASS_UID:
+            DCMNET_INFO("Refusing Association (no implementation class UID provided)");
+            break;
+        case DCMSCP_NO_PRESENTATION_CONTEXTS:
+            DCMNET_INFO("Refusing Association (no acceptable presentation contexts)");
+            break;
+        case DCMSCP_INTERNAL_ERROR:
+            DCMNET_INFO("Refusing Association (internal error)");
+            break;
+        default:
+            DCMNET_INFO("Refusing Association (unknown reason)");
+            break;
+    }
+
+    // Set some values in the reject message depending on the reason
+    switch (reason)
+    {
+        case DCMSCP_TOO_MANY_ASSOCIATIONS:
+            rej.result = ASC_RESULT_REJECTEDTRANSIENT;
+            rej.source = ASC_SOURCE_SERVICEPROVIDER_PRESENTATION_RELATED;
+            rej.reason = ASC_REASON_SP_PRES_LOCALLIMITEXCEEDED;
+            break;
+        case DCMSCP_CANNOT_FORK:
+            rej.result = ASC_RESULT_REJECTEDPERMANENT;
+            rej.source = ASC_SOURCE_SERVICEPROVIDER_PRESENTATION_RELATED;
+            rej.reason = ASC_REASON_SP_PRES_TEMPORARYCONGESTION;
+            break;
+        case DCMSCP_BAD_APPLICATION_CONTEXT_NAME:
+            rej.result = ASC_RESULT_REJECTEDTRANSIENT;
+            rej.source = ASC_SOURCE_SERVICEUSER;
+            rej.reason = ASC_REASON_SU_APPCONTEXTNAMENOTSUPPORTED;
+            break;
+        case DCMSCP_CALLED_AE_TITLE_NOT_RECOGNIZED:
+            rej.result = ASC_RESULT_REJECTEDPERMANENT;
+            rej.source = ASC_SOURCE_SERVICEUSER;
+            rej.reason = ASC_REASON_SU_CALLEDAETITLENOTRECOGNIZED;
+            break;
+        case DCMSCP_CALLING_AE_TITLE_NOT_RECOGNIZED:
+            rej.result = ASC_RESULT_REJECTEDPERMANENT;
+            rej.source = ASC_SOURCE_SERVICEUSER;
+            rej.reason = ASC_REASON_SU_CALLINGAETITLENOTRECOGNIZED;
+            break;
+        case DCMSCP_FORCED:
+        case DCMSCP_NO_IMPLEMENTATION_CLASS_UID:
+        case DCMSCP_NO_PRESENTATION_CONTEXTS:
+        case DCMSCP_CALLING_HOST_NOT_ALLOWED:
+        case DCMSCP_INTERNAL_ERROR:
+        default:
+            rej.result = ASC_RESULT_REJECTEDPERMANENT;
+            rej.source = ASC_SOURCE_SERVICEUSER;
+            rej.reason = ASC_REASON_SU_NOREASON;
+            break;
+    }
+
+    // Reject the association request.
+    ASC_rejectAssociation(m_assoc, &rej);
 }
 
+// ----------------------------------------------------------------------------
+
+OFCondition DcmSCP::waitForAssociationRQ(T_ASC_Network* network)
+{
+    if (network == NULL)
+        return ASC_NULLKEY;
+    if (m_assoc != NULL)
+        return DIMSE_ILLEGALASSOCIATION;
+
+    Uint32 timeout = m_cfg->getConnectionTimeout();
+    OFBool useSecureLayer = m_cfg->transportLayerEnabled();
+
+    // Listen to a socket for timeout seconds and wait for an association request
+    OFCondition cond = ASC_receiveAssociation(network,
+                                              &m_assoc,
+                                              m_cfg->getMaxReceivePDULength(),
+                                              NULL,
+                                              NULL,
+                                              useSecureLayer,
+                                              m_cfg->getConnectionBlockingMode(),
+                                              OFstatic_cast(int, timeout));
+
+    // In case of a timeout in non-blocking mode, call notifier (and return
+    // to main event loop later)
+    if (cond == DUL_NOASSOCIATIONREQUEST)
+    {
+        notifyConnectionTimeout();
+    }
+    else
+    {
+        // If association could be received, handle it
+        if (cond.good())
+        {
+            cond = processAssociationRQ();
+            // There was an association which has ended now:
+            // Call notifier and output separator line.
+            notifyAssociationTermination();
+            DCMNET_DEBUG("+++++++++++++++++++++++++++++");
+        }
+        // Else, if we could not receive an association request since there was
+        // some error, just ignore it (and continue in main event loop later)
+        else
+        {
+            DCMNET_ERROR("Could not receive association request: " << cond.text());
+            cond = EC_Normal;
+        }
+    }
+
+    // We are done with this association, free it and set to NULL.
+    // ASC_receiveAssociation will always create a related structure, even
+    // if no association was received at all.
+    dropAndDestroyAssociation();
+    return cond;
+}
 
 OFCondition DcmSCP::processAssociationRQ()
 {
-  DcmSCPActionType desiredAction = DCMSCP_ACTION_UNDEFINED;
-  if ( (m_assoc == NULL) || (m_assoc->params == NULL) )
-    return ASC_NULLKEY;
+    DcmSCPActionType desiredAction = DCMSCP_ACTION_UNDEFINED;
+    if ((m_assoc == NULL) || (m_assoc->params == NULL))
+        return ASC_NULLKEY;
 
-  // call notifier function
-  notifyAssociationRequest(*m_assoc->params, desiredAction);
-  if (desiredAction != DCMSCP_ACTION_UNDEFINED)
-  {
-    if (desiredAction == DCMSCP_ACTION_REFUSE_ASSOCIATION)
+    // call notifier function
+    notifyAssociationRequest(*m_assoc->params, desiredAction);
+    if (desiredAction != DCMSCP_ACTION_UNDEFINED)
     {
-      refuseAssociation( DCMSCP_INTERNAL_ERROR );
-      return EC_Normal;
+        if (desiredAction == DCMSCP_ACTION_REFUSE_ASSOCIATION)
+        {
+            refuseAssociation(DCMSCP_INTERNAL_ERROR);
+            return EC_Normal;
+        }
+        else
+            desiredAction = DCMSCP_ACTION_UNDEFINED; // reset for later use
     }
-    else desiredAction = DCMSCP_ACTION_UNDEFINED; // reset for later use
-  }
 
-  // Now we have to figure out if we might have to refuse the association request.
-  // This is the case if at least one of five conditions is met:
+    // Now we have to figure out if we might have to refuse the association request.
+    // This is the case if at least one of five conditions is met:
 
-  // Condition 1: if option "--refuse" is set we want to refuse the association request.
-  if( m_cfg->getRefuseAssociation() )
-  {
-    refuseAssociation( DCMSCP_FORCED );
-    return EC_Normal;
-  }
-
-  // Condition 2: determine the application context name. If an error occurred or if the
-  // application context name is not supported we want to refuse the association request.
-  char buf[BUFSIZ];
-  OFCondition cond = ASC_getApplicationContextName( m_assoc->params, buf , sizeof(buf));
-  if( cond.bad() || strcmp( buf, DICOM_STDAPPLICATIONCONTEXT ) != 0 )
-  {
-    refuseAssociation( DCMSCP_BAD_APPLICATION_CONTEXT_NAME );
-    return EC_Normal;
-  }
+    // Condition 1: if option "--refuse" is set we want to refuse the association request.
+    if (m_cfg->getRefuseAssociation())
+    {
+        refuseAssociation(DCMSCP_FORCED);
+        return EC_Normal;
+    }
 
-  // Condition 3: if the calling host is not supported, we want to refuse
-  // the association request
-  if (!checkCallingHostAccepted(m_assoc->params->DULparams.calledPresentationAddress))
-  {
-    refuseAssociation( DCMSCP_CALLING_HOST_NOT_ALLOWED );
-    return EC_Normal;
-  }
+    // Condition 2: determine the application context name. If an error occurred or if the
+    // application context name is not supported we want to refuse the association request.
+    char buf[BUFSIZ];
+    OFCondition cond = ASC_getApplicationContextName(m_assoc->params, buf, sizeof(buf));
+    if (cond.bad() || strcmp(buf, DICOM_STDAPPLICATIONCONTEXT) != 0)
+    {
+        refuseAssociation(DCMSCP_BAD_APPLICATION_CONTEXT_NAME);
+        return EC_Normal;
+    }
 
-  // Condition 4: if the calling or called application entity title is not supported
-  // we want to refuse the association request
-  if (!checkCalledAETitleAccepted(m_assoc->params->DULparams.calledAPTitle))
-  {
-    refuseAssociation( DCMSCP_CALLED_AE_TITLE_NOT_RECOGNIZED );
-    return EC_Normal;
-  }
+    // Condition 3: if the calling host is not supported, we want to refuse
+    // the association request
+    if (!checkCallingHostAccepted(m_assoc->params->DULparams.calledPresentationAddress))
+    {
+        refuseAssociation(DCMSCP_CALLING_HOST_NOT_ALLOWED);
+        return EC_Normal;
+    }
 
-  if (!checkCallingAETitleAccepted(m_assoc->params->DULparams.callingAPTitle))
-  {
-    refuseAssociation( DCMSCP_CALLING_AE_TITLE_NOT_RECOGNIZED );
-    return EC_Normal;
-  }
-
-  /* set our application entity title */
-  if (m_cfg->getRespondWithCalledAETitle())
-    ASC_setAPTitles(m_assoc->params, NULL, NULL, m_assoc->params->DULparams.calledAPTitle);
-  else
-    ASC_setAPTitles(m_assoc->params, NULL, NULL, m_cfg->getAETitle().c_str());
-
-  /* If we get to this point the association shall be negotiated.
-     Thus, for every presentation context it is checked whether
-     it can be accepted. However, this is only a "dry" run, i.e.
-     there is not yet sent a response message to the SCU
-   */
-  cond = negotiateAssociation();
-  if( cond.bad() )
-  {
-    return EC_Normal;
-  }
+    // Condition 4: if the calling or called application entity title is not supported
+    // we want to refuse the association request
+    if (!checkCalledAETitleAccepted(m_assoc->params->DULparams.calledAPTitle))
+    {
+        refuseAssociation(DCMSCP_CALLED_AE_TITLE_NOT_RECOGNIZED);
+        return EC_Normal;
+    }
+
+    if (!checkCallingAETitleAccepted(m_assoc->params->DULparams.callingAPTitle))
+    {
+        refuseAssociation(DCMSCP_CALLING_AE_TITLE_NOT_RECOGNIZED);
+        return EC_Normal;
+    }
+
+    /* set our application entity title */
+    if (m_cfg->getRespondWithCalledAETitle())
+        ASC_setAPTitles(m_assoc->params, NULL, NULL, m_assoc->params->DULparams.calledAPTitle);
+    else
+        ASC_setAPTitles(m_assoc->params, NULL, NULL, m_cfg->getAETitle().c_str());
+
+    /* If we get to this point the association shall be negotiated.
+       Thus, for every presentation context it is checked whether
+       it can be accepted. However, this is only a "dry" run, i.e.
+       there is not yet sent a response message to the SCU
+     */
+    cond = negotiateAssociation();
+    if (cond.bad())
+    {
+        return EC_Normal;
+    }
+
+    // Reject association if no presentation context was negotiated
+    if (ASC_countAcceptedPresentationContexts(m_assoc->params) == 0)
+    {
+        // Dump some debug information
+        OFString tempStr;
+        DCMNET_INFO("No Acceptable Presentation Contexts");
+        if (m_cfg->getVerbosePCMode())
+            DCMNET_INFO(ASC_dumpParameters(tempStr, m_assoc->params, ASC_ASSOC_RJ));
+        else
+            DCMNET_DEBUG(ASC_dumpParameters(tempStr, m_assoc->params, ASC_ASSOC_RJ));
+        refuseAssociation(DCMSCP_NO_PRESENTATION_CONTEXTS);
+        return EC_Normal;
+    }
+
+    // If the negotiation was successful, accept the association request
+    cond = ASC_acknowledgeAssociation(m_assoc);
+    if (cond.bad())
+    {
+        return EC_Normal;
+    }
+    notifyAssociationAcknowledge();
 
-  // Reject association if no presentation context was negotiated
-  if( ASC_countAcceptedPresentationContexts( m_assoc->params ) == 0 )
-  {
     // Dump some debug information
     OFString tempStr;
-    DCMNET_INFO("No Acceptable Presentation Contexts");
+    DCMNET_INFO("Association Acknowledged (Max Send PDV: " << OFstatic_cast(Uint32, m_assoc->sendPDVLength) << ")");
     if (m_cfg->getVerbosePCMode())
-      DCMNET_INFO(ASC_dumpParameters(tempStr, m_assoc->params, ASC_ASSOC_RJ));
+        DCMNET_INFO(ASC_dumpParameters(tempStr, m_assoc->params, ASC_ASSOC_AC));
     else
-      DCMNET_DEBUG(ASC_dumpParameters(tempStr, m_assoc->params, ASC_ASSOC_RJ));
-    refuseAssociation( DCMSCP_NO_PRESENTATION_CONTEXTS );
-    return EC_Normal;
-  }
-
-  // If the negotiation was successful, accept the association request
-  cond = ASC_acknowledgeAssociation( m_assoc );
-  if( cond.bad() )
-  {
-    return EC_Normal;
-  }
-  notifyAssociationAcknowledge();
+        DCMNET_DEBUG(ASC_dumpParameters(tempStr, m_assoc->params, ASC_ASSOC_AC));
 
-  // Dump some debug information
-  OFString tempStr;
-  DCMNET_INFO("Association Acknowledged (Max Send PDV: " << OFstatic_cast(Uint32, m_assoc->sendPDVLength) << ")");
-  if (m_cfg->getVerbosePCMode())
-    DCMNET_INFO(ASC_dumpParameters(tempStr, m_assoc->params, ASC_ASSOC_AC));
-  else
-    DCMNET_DEBUG(ASC_dumpParameters(tempStr, m_assoc->params, ASC_ASSOC_AC));
+    // Go ahead and handle the association (i.e. handle the caller's requests) in this process
+    handleAssociation();
 
-  // Go ahead and handle the association (i.e. handle the caller's requests) in this process
-  handleAssociation();
-
-  return EC_Normal;
+    return EC_Normal;
 }
 
 // ----------------------------------------------------------------------------
 
 OFCondition DcmSCP::negotiateAssociation()
 {
-  // Check whether there is something to negotiate...
-  if (m_assoc == NULL)
-    return DIMSE_ILLEGALASSOCIATION;
+    // Check whether there is something to negotiate...
+    if (m_assoc == NULL)
+        return DIMSE_ILLEGALASSOCIATION;
 
-  // Set presentation contexts as defined in association configuration
-  OFCondition result = m_cfg->evaluateIncomingAssociation(*m_assoc);
-  if (result.bad())
-  {
-    OFString tempStr;
-    DCMNET_ERROR(DimseCondition::dump(tempStr, result));
-  }
-  return result;
+    // Set presentation contexts as defined in association configuration
+    OFCondition result = m_cfg->evaluateIncomingAssociation(*m_assoc);
+    if (result.bad())
+    {
+        OFString tempStr;
+        DCMNET_ERROR(DimseCondition::dump(tempStr, result));
+    }
+    return result;
 }
 
 // ----------------------------------------------------------------------------
@@ -503,18 +561,19 @@ OFCondition DcmSCP::abortAssociation()
     // Check whether there is an active association
     if (isConnected())
     {
-      // Abort current association
-      DCMNET_INFO("Aborting Association (initiated by SCP)");
-      cond = ASC_abortAssociation(m_assoc);
-      // Notify user in case of error
-      if (cond.bad())
-      {
-        OFString tempStr;
-        DCMNET_ERROR("Association Abort Failed: " << DimseCondition::dump(tempStr, cond));
-      }
-      // Note: association is dropped and memory freed somewhere else
-    } else
-      DCMNET_WARN("DcmSCP::abortAssociation() called but SCP actually has no association running, ignoring");
+        // Abort current association
+        DCMNET_INFO("Aborting Association (initiated by SCP)");
+        cond = ASC_abortAssociation(m_assoc);
+        // Notify user in case of error
+        if (cond.bad())
+        {
+            OFString tempStr;
+            DCMNET_ERROR("Association Abort Failed: " << DimseCondition::dump(tempStr, cond));
+        }
+        // Note: association is dropped and memory freed somewhere else
+    }
+    else
+        DCMNET_WARN("DcmSCP::abortAssociation() called but SCP actually has no association running, ignoring");
     return cond;
 }
 
@@ -522,889 +581,914 @@ OFCondition DcmSCP::abortAssociation()
 
 void DcmSCP::handleAssociation()
 {
-  if (m_assoc == NULL)
-  {
-    DCMNET_WARN("DcmSCP::handleAssociation() called but SCP actually has no association running, ignoring");
-    return;
-  }
-
-  // Receive a DIMSE command and perform all the necessary actions. (Note that ReceiveAndHandleCommands()
-  // will always return a value 'cond' for which 'cond.bad()' will be true. This value indicates that either
-  // some kind of error occurred, or that the peer aborted the association (DUL_PEERABORTEDASSOCIATION),
-  // or that the peer requested the release of the association (DUL_PEERREQUESTEDRELEASE).) (Also note
-  // that ReceiveAndHandleCommands() will never return EC_Normal.)
-  OFCondition cond = EC_Normal;
-  T_DIMSE_Message message;
-  T_ASC_PresentationContextID presID;
-
-  // start a loop to be able to receive more than one DIMSE command
-  while( cond.good() )
-  {
-    // receive a DIMSE command over the network
-    cond = DIMSE_receiveCommand( m_assoc, m_cfg->getDIMSEBlockingMode(), m_cfg->getDIMSETimeout(),
-                                 &presID, &message, NULL );
-
-    // check if peer did release or abort, or if we have a valid message
-    if( cond.good() )
-    {
-      DcmPresentationContextInfo presInfo;
-      getPresentationContextInfo(m_assoc, presID, presInfo);
-      cond = handleIncomingCommand(&message, presInfo);
-    }
-  }
-  // Clean up on association termination.
-  if( cond == DUL_PEERREQUESTEDRELEASE )
-  {
-    notifyReleaseRequest();
-    ASC_acknowledgeRelease(m_assoc);
-  }
-  else if( cond == DUL_PEERABORTEDASSOCIATION )
-  {
-    notifyAbortRequest();
-  }
-  else
-  {
-    notifyDIMSEError(cond);
-    ASC_abortAssociation( m_assoc );
-  }
-}
-
-// ----------------------------------------------------------------------------
-
-OFCondition DcmSCP::handleIncomingCommand(T_DIMSE_Message *incomingMsg,
-                                          const DcmPresentationContextInfo &presInfo)
-{
-  OFCondition cond;
-  // Handle C-ECHO for Verification SOP Class
-  if ( (incomingMsg->CommandField == DIMSE_C_ECHO_RQ)
-       && (presInfo.abstractSyntax == UID_VerificationSOPClass) )
-  {
-    // Process C-ECHO request
-    cond = handleECHORequest(incomingMsg->msg.CEchoRQ, presInfo.presentationContextID);
-  } else {
-    // We cannot handle this kind of message. Note that the condition will be returned
-    // and that the caller is responsible to end the association if desired.
-    OFString tempStr;
-    DCMNET_ERROR("Cannot handle this kind of DIMSE command (0x"
-      << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
-      << OFstatic_cast(unsigned int, incomingMsg->CommandField) << ")");
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, *incomingMsg, DIMSE_INCOMING));
-    cond = DIMSE_BADCOMMANDTYPE;
-  }
-
-  // return result
-  return cond;
+    if (m_assoc == NULL)
+    {
+        DCMNET_WARN("DcmSCP::handleAssociation() called but SCP actually has no association running, ignoring");
+        return;
+    }
+
+    // Receive a DIMSE command and perform all the necessary actions. (Note that ReceiveAndHandleCommands()
+    // will always return a value 'cond' for which 'cond.bad()' will be true. This value indicates that either
+    // some kind of error occurred, or that the peer aborted the association (DUL_PEERABORTEDASSOCIATION),
+    // or that the peer requested the release of the association (DUL_PEERREQUESTEDRELEASE).) (Also note
+    // that ReceiveAndHandleCommands() will never return EC_Normal.)
+    OFCondition cond = EC_Normal;
+    T_DIMSE_Message message;
+    T_ASC_PresentationContextID presID;
+
+    // start a loop to be able to receive more than one DIMSE command
+    while (cond.good())
+    {
+        // receive a DIMSE command over the network
+        cond = DIMSE_receiveCommand(
+            m_assoc, m_cfg->getDIMSEBlockingMode(), m_cfg->getDIMSETimeout(), &presID, &message, NULL);
+
+        // check if peer did release or abort, or if we have a valid message
+        if (cond.good())
+        {
+            DcmPresentationContextInfo presInfo;
+            getPresentationContextInfo(m_assoc, presID, presInfo);
+            cond = handleIncomingCommand(&message, presInfo);
+        }
+    }
+    // Clean up on association termination.
+    if (cond == DUL_PEERREQUESTEDRELEASE)
+    {
+        notifyReleaseRequest();
+        ASC_acknowledgeRelease(m_assoc);
+    }
+    else if (cond == DUL_PEERABORTEDASSOCIATION)
+    {
+        notifyAbortRequest();
+    }
+    else
+    {
+        notifyDIMSEError(cond);
+        ASC_abortAssociation(m_assoc);
+    }
+}
+
+// ----------------------------------------------------------------------------
+
+OFCondition DcmSCP::handleIncomingCommand(T_DIMSE_Message* incomingMsg, const DcmPresentationContextInfo& presInfo)
+{
+    OFCondition cond;
+    // Handle C-ECHO for Verification SOP Class
+    if ((incomingMsg->CommandField == DIMSE_C_ECHO_RQ) && (presInfo.abstractSyntax == UID_VerificationSOPClass))
+    {
+        // Process C-ECHO request
+        cond = handleECHORequest(incomingMsg->msg.CEchoRQ, presInfo.presentationContextID);
+    }
+    else
+    {
+        // We cannot handle this kind of message. Note that the condition will be returned
+        // and that the caller is responsible to end the association if desired.
+        OFString tempStr;
+        DCMNET_ERROR("Cannot handle this kind of DIMSE command (0x"
+                     << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
+                     << OFstatic_cast(unsigned int, incomingMsg->CommandField) << ")");
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, *incomingMsg, DIMSE_INCOMING));
+        cond = DIMSE_BADCOMMANDTYPE;
+    }
+
+    // return result
+    return cond;
 }
 
 // ----------------------------------------------------------------------------
 
 // -- C-ECHO --
 
-OFCondition DcmSCP::handleECHORequest(T_DIMSE_C_EchoRQ &reqMessage,
-                                      const T_ASC_PresentationContextID presID)
+OFCondition DcmSCP::handleECHORequest(T_DIMSE_C_EchoRQ& reqMessage, const T_ASC_PresentationContextID presID)
 {
-  OFCondition cond;
-  OFString tempStr;
+    OFCondition cond;
+    OFString tempStr;
 
-  // Dump debug information
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-  {
-    DCMNET_INFO("Received C-ECHO Request");
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
-    DCMNET_INFO("Sending C-ECHO Response");
-  } else {
-    DCMNET_INFO("Received C-ECHO Request (MsgID " << reqMessage.MessageID << ")");
-    DCMNET_INFO("Sending C-ECHO Response (" << DU_cechoStatusString(STATUS_Success) << ")");
-  }
-
-  // Send response message
-  cond = DIMSE_sendEchoResponse( m_assoc, presID, &reqMessage, STATUS_Success, NULL );
-  if( cond.bad() )
-    DCMNET_ERROR("Cannot send C-ECHO Response: " << DimseCondition::dump(tempStr, cond));
-  else
-    DCMNET_DEBUG("C-ECHO Response successfully sent");
+    // Dump debug information
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+    {
+        DCMNET_INFO("Received C-ECHO Request");
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+        DCMNET_INFO("Sending C-ECHO Response");
+    }
+    else
+    {
+        DCMNET_INFO("Received C-ECHO Request (MsgID " << reqMessage.MessageID << ")");
+        DCMNET_INFO("Sending C-ECHO Response (" << DU_cechoStatusString(STATUS_Success) << ")");
+    }
 
-  return cond;
+    // Send response message
+    cond = DIMSE_sendEchoResponse(m_assoc, presID, &reqMessage, STATUS_Success, NULL);
+    if (cond.bad())
+        DCMNET_ERROR("Cannot send C-ECHO Response: " << DimseCondition::dump(tempStr, cond));
+    else
+        DCMNET_DEBUG("C-ECHO Response successfully sent");
+
+    return cond;
 }
 
 // ----------------------------------------------------------------------------
 
 // -- C-STORE --
 
-OFCondition DcmSCP::handleSTORERequest(T_DIMSE_C_StoreRQ &reqMessage,
+OFCondition DcmSCP::handleSTORERequest(T_DIMSE_C_StoreRQreqMessage,
                                        const T_ASC_PresentationContextID presID,
-                                       DcmDataset *&reqDataset)
+                                       DcmDataset*& reqDataset)
 {
-  // First, receive the C-STORE request
-  OFCondition cond = receiveSTORERequest(reqMessage, presID, reqDataset);
+    // First, receive the C-STORE request
+    OFCondition cond = receiveSTORERequest(reqMessage, presID, reqDataset);
 
-  if (cond.good())
-  {
-    // Then, check the request message and dataset and return an DIMSE status code
-    const Uint16 rspStatusCode = checkSTORERequest(reqMessage, reqDataset);
-    // ... that is sent back with the C-STORE response message
-    cond = sendSTOREResponse(presID, reqMessage, rspStatusCode);
-  }
+    if (cond.good())
+    {
+        // Then, check the request message and dataset and return an DIMSE status code
+        const Uint16 rspStatusCode = checkSTORERequest(reqMessage, reqDataset);
+        // ... that is sent back with the C-STORE response message
+        cond = sendSTOREResponse(presID, reqMessage, rspStatusCode);
+    }
 
-  return cond;
+    return cond;
 }
 
-
-OFCondition DcmSCP::receiveSTORERequest(T_DIMSE_C_StoreRQ &reqMessage,
+OFCondition DcmSCP::receiveSTORERequest(T_DIMSE_C_StoreRQ& reqMessage,
                                         const T_ASC_PresentationContextID presID,
-                                        DcmDataset *&reqDataset)
-{
-  // Do some basic validity checks
-  if (m_assoc == NULL)
-    return DIMSE_ILLEGALASSOCIATION;
-
-  OFCondition cond;
-  OFString tempStr;
-  T_ASC_PresentationContextID presIDdset;
-  // Remember the passed dataset pointer
-  DcmDataset *dataset = reqDataset;
-
-  // Dump debug information
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-    DCMNET_INFO("Received C-STORE Request");
-  else
-    DCMNET_INFO("Received C-STORE Request (MsgID " << reqMessage.MessageID << ")");
-
-  // Check if dataset is announced correctly
-  if (reqMessage.DataSetType == DIMSE_DATASET_NULL)
-  {
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
-    DCMNET_ERROR("Received C-STORE request but no dataset announced, aborting");
-    return DIMSE_BADMESSAGE;
-  }
-
-  // Receive dataset (in memory)
-  cond = receiveDIMSEDataset(&presIDdset, &dataset);
-  if (cond.bad())
-  {
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
-    DCMNET_ERROR("Unable to receive C-STORE dataset on presentation context " << OFstatic_cast(unsigned int, presID));
-    return cond;
-  }
+                                        DcmDataset*& reqDataset)
+{
+    // Do some basic validity checks
+    if (m_assoc == NULL)
+        return DIMSE_ILLEGALASSOCIATION;
 
-  // Output request message only if trace level is enabled
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, dataset, presID));
-  else
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+    OFCondition cond;
+    OFString tempStr;
+    T_ASC_PresentationContextID presIDdset;
+    // Remember the passed dataset pointer
+    DcmDataset* dataset = reqDataset;
+
+    // Dump debug information
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+        DCMNET_INFO("Received C-STORE Request");
+    else
+        DCMNET_INFO("Received C-STORE Request (MsgID " << reqMessage.MessageID << ")");
 
-  // Compare presentation context ID of command and data set
-  if (presIDdset != presID)
-  {
-    DCMNET_ERROR("Presentation Context ID of command (" << OFstatic_cast(unsigned int, presID)
-      << ") and data set (" << OFstatic_cast(unsigned int, presIDdset) << ") differs");
-    if (dataset != reqDataset)
+    // Check if dataset is announced correctly
+    if (reqMessage.DataSetType == DIMSE_DATASET_NULL)
     {
-      // Free memory allocated by receiveDIMSEDataset()
-      delete dataset;
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+        DCMNET_ERROR("Received C-STORE request but no dataset announced, aborting");
+        return DIMSE_BADMESSAGE;
     }
-    return makeDcmnetCondition(DIMSEC_INVALIDPRESENTATIONCONTEXTID, OF_error,
-      "DIMSE: Presentation Contexts of Command and Data Set differ");
-  }
 
-  // Set return value
-  reqDataset = dataset;
+    // Receive dataset (in memory)
+    cond = receiveDIMSEDataset(&presIDdset, &dataset);
+    if (cond.bad())
+    {
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+        DCMNET_ERROR("Unable to receive C-STORE dataset on presentation context "
+                     << OFstatic_cast(unsigned int, presID));
+        return cond;
+    }
 
-  return cond;
-}
+    // Output request message only if trace level is enabled
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, dataset, presID));
+    else
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
 
+    // Compare presentation context ID of command and data set
+    if (presIDdset != presID)
+    {
+        DCMNET_ERROR("Presentation Context ID of command (" << OFstatic_cast(unsigned int, presID) << ") and data set ("
+                                                            << OFstatic_cast(unsigned int, presIDdset) << ") differs");
+        if (dataset != reqDataset)
+        {
+            // Free memory allocated by receiveDIMSEDataset()
+            delete dataset;
+        }
+        return makeDcmnetCondition(DIMSEC_INVALIDPRESENTATIONCONTEXTID,
+                                   OF_error,
+                                   "DIMSE: Presentation Contexts of Command and Data Set differ");
+    }
+
+    // Set return value
+    reqDataset = dataset;
 
-OFCondition DcmSCP::receiveSTORERequest(T_DIMSE_C_StoreRQ &reqMessage,
-                                        const T_ASC_PresentationContextID presID,
-                                        const OFString &filename)
-{
-  // Do some basic validity checks
-  if (m_assoc == NULL)
-    return DIMSE_ILLEGALASSOCIATION;
-
-  OFCondition cond;
-  OFString tempStr;
-  // Use presentation context ID of the command set as a default
-  T_ASC_PresentationContextID presIDdset = presID;
-
-  // Dump debug information
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-    DCMNET_INFO("Received C-STORE Request");
-  else
-    DCMNET_INFO("Received C-STORE Request (MsgID " << reqMessage.MessageID << ")");
-
-  // Check if dataset is announced correctly
-  if (reqMessage.DataSetType == DIMSE_DATASET_NULL)
-  {
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
-    DCMNET_ERROR("Received C-STORE request but no dataset announced, aborting");
-    return DIMSE_BADMESSAGE;
-  }
-
-  // Receive dataset (directly to file)
-  cond = receiveSTORERequestDataset(&presIDdset, reqMessage, filename);
-  if (cond.bad())
-  {
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
-    DCMNET_ERROR("Unable to receive C-STORE dataset on presentation context " << OFstatic_cast(unsigned int, presID));
     return cond;
-  }
+}
 
-  // Output request message only if trace level is enabled
-  DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+OFCondition DcmSCP::receiveSTORERequest(T_DIMSE_C_StoreRQ& reqMessage,
+                                        const T_ASC_PresentationContextID presID,
+                                        const OFString& filename)
+{
+    // Do some basic validity checks
+    if (m_assoc == NULL)
+        return DIMSE_ILLEGALASSOCIATION;
 
-  // Compare presentation context ID of command and data set
-  if (presIDdset != presID)
-  {
-    DCMNET_ERROR("Presentation Context ID of command (" << OFstatic_cast(unsigned int, presID)
-      << ") and data set (" << OFstatic_cast(unsigned int, presIDdset) << ") differs");
-    return makeDcmnetCondition(DIMSEC_INVALIDPRESENTATIONCONTEXTID, OF_error,
-      "DIMSE: Presentation Contexts of Command and Data Set differ");
-  }
+    OFCondition cond;
+    OFString tempStr;
+    // Use presentation context ID of the command set as a default
+    T_ASC_PresentationContextID presIDdset = presID;
 
-  return cond;
-}
+    // Dump debug information
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+        DCMNET_INFO("Received C-STORE Request");
+    else
+        DCMNET_INFO("Received C-STORE Request (MsgID " << reqMessage.MessageID << ")");
+
+    // Check if dataset is announced correctly
+    if (reqMessage.DataSetType == DIMSE_DATASET_NULL)
+    {
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+        DCMNET_ERROR("Received C-STORE request but no dataset announced, aborting");
+        return DIMSE_BADMESSAGE;
+    }
+
+    // Receive dataset (directly to file)
+    cond = receiveSTORERequestDataset(&presIDdset, reqMessage, filename);
+    if (cond.bad())
+    {
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+        DCMNET_ERROR("Unable to receive C-STORE dataset on presentation context "
+                     << OFstatic_cast(unsigned int, presID));
+        return cond;
+    }
+
+    // Output request message only if trace level is enabled
+    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+
+    // Compare presentation context ID of command and data set
+    if (presIDdset != presID)
+    {
+        DCMNET_ERROR("Presentation Context ID of command (" << OFstatic_cast(unsigned int, presID) << ") and data set ("
+                                                            << OFstatic_cast(unsigned int, presIDdset) << ") differs");
+        return makeDcmnetCondition(DIMSEC_INVALIDPRESENTATIONCONTEXTID,
+                                   OF_error,
+                                   "DIMSE: Presentation Contexts of Command and Data Set differ");
+    }
 
+    return cond;
+}
 
 OFCondition DcmSCP::sendSTOREResponse(const T_ASC_PresentationContextID presID,
-                                      const T_DIMSE_C_StoreRQ &reqMessage,
+                                      const T_DIMSE_C_StoreRQreqMessage,
                                       const Uint16 rspStatusCode)
 {
-  // Call the method doing the real work
-  return sendSTOREResponse(presID, reqMessage.MessageID, reqMessage.AffectedSOPClassUID, reqMessage.AffectedSOPInstanceUID,
-    rspStatusCode, NULL /* statusDetail */);
+    // Call the method doing the real work
+    return sendSTOREResponse(presID,
+                             reqMessage.MessageID,
+                             reqMessage.AffectedSOPClassUID,
+                             reqMessage.AffectedSOPInstanceUID,
+                             rspStatusCode,
+                             NULL /* statusDetail */);
 }
 
-
 OFCondition DcmSCP::sendSTOREResponse(const T_ASC_PresentationContextID presID,
                                       const Uint16 messageID,
-                                      const OFString &sopClassUID,
-                                      const OFString &sopInstanceUID,
+                                      const OFStringsopClassUID,
+                                      const OFStringsopInstanceUID,
                                       const Uint16 rspStatusCode,
-                                      DcmDataset *statusDetail)
-{
-  OFCondition cond;
-  OFString tempStr;
-
-  // Send back response
-  T_DIMSE_Message response;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&response, sizeof(response));
-  T_DIMSE_C_StoreRSP &storeRsp = response.msg.CStoreRSP;
-  response.CommandField = DIMSE_C_STORE_RSP;
-  storeRsp.MessageIDBeingRespondedTo = messageID;
-  storeRsp.DimseStatus = rspStatusCode;
-  storeRsp.DataSetType = DIMSE_DATASET_NULL;
-  // Always send the optional fields "Affected SOP Class UID" and "Affected SOP Instance UID"
-  storeRsp.opts = O_STORE_AFFECTEDSOPCLASSUID | O_STORE_AFFECTEDSOPINSTANCEUID;
-  OFStandard::strlcpy(storeRsp.AffectedSOPClassUID, sopClassUID.c_str(), sizeof(storeRsp.AffectedSOPClassUID));
-  OFStandard::strlcpy(storeRsp.AffectedSOPInstanceUID, sopInstanceUID.c_str(), sizeof(storeRsp.AffectedSOPInstanceUID));
-
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-  {
-    DCMNET_INFO("Sending C-STORE Response");
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_OUTGOING, NULL, presID));
-  } else {
-    DCMNET_INFO("Sending C-STORE Response (" << DU_cstoreStatusString(rspStatusCode) << ")");
-  }
-
-  // Send response message
-  cond = sendDIMSEMessage(presID, &response, NULL /* dataObject */, statusDetail);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed sending C-STORE response: " << DimseCondition::dump(tempStr, cond));
-  }
+                                      DcmDataset* statusDetail)
+{
+    OFCondition cond;
+    OFString tempStr;
 
-  return cond;
-}
+    // Send back response
+    T_DIMSE_Message response;
+    // Make sure everything is zeroed (especially options)
+    bzero((char*)&response, sizeof(response));
+    T_DIMSE_C_StoreRSP& storeRsp       = response.msg.CStoreRSP;
+    response.CommandField              = DIMSE_C_STORE_RSP;
+    storeRsp.MessageIDBeingRespondedTo = messageID;
+    storeRsp.DimseStatus               = rspStatusCode;
+    storeRsp.DataSetType               = DIMSE_DATASET_NULL;
+    // Always send the optional fields "Affected SOP Class UID" and "Affected SOP Instance UID"
+    storeRsp.opts = O_STORE_AFFECTEDSOPCLASSUID | O_STORE_AFFECTEDSOPINSTANCEUID;
+    OFStandard::strlcpy(storeRsp.AffectedSOPClassUID, sopClassUID.c_str(), sizeof(storeRsp.AffectedSOPClassUID));
+    OFStandard::strlcpy(
+        storeRsp.AffectedSOPInstanceUID, sopInstanceUID.c_str(), sizeof(storeRsp.AffectedSOPInstanceUID));
 
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+    {
+        DCMNET_INFO("Sending C-STORE Response");
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_OUTGOING, NULL, presID));
+    }
+    else
+    {
+        DCMNET_INFO("Sending C-STORE Response (" << DU_cstoreStatusString(rspStatusCode) << ")");
+    }
+
+    // Send response message
+    cond = sendDIMSEMessage(presID, &response, NULL /* dataObject */, statusDetail);
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Failed sending C-STORE response: " << DimseCondition::dump(tempStr, cond));
+    }
 
-Uint16 DcmSCP::checkSTORERequest(T_DIMSE_C_StoreRQ & /*reqMessage*/,
-                                 DcmDataset * /*reqDataset*/)
+    return cond;
+}
+
+Uint16 DcmSCP::checkSTORERequest(T_DIMSE_C_StoreRQ& /*reqMessage*/, DcmDataset* /*reqDataset*/)
 {
-  // we default to success
-  return STATUS_Success;
+    // we default to success
+    return STATUS_Success;
 }
 
 // ----------------------------------------------------------------------------
 
 // -- C-FIND --
 
-OFCondition DcmSCP::receiveFINDRequest(T_DIMSE_C_FindRQ &reqMessage,
+OFCondition DcmSCP::receiveFINDRequest(T_DIMSE_C_FindRQreqMessage,
                                        const T_ASC_PresentationContextID presID,
-                                       DcmDataset *&reqDataset)
-{
-  // Do some basic validity checks
-  if (m_assoc == NULL)
-    return DIMSE_ILLEGALASSOCIATION;
-
-  OFCondition cond;
-  OFString tempStr;
-  T_ASC_PresentationContextID presIDdset;
-  DcmDataset *dataset = NULL;
-
-  // Dump debug information
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-    DCMNET_INFO("Received C-FIND Request");
-  else
-    DCMNET_INFO("Received C-FIND Request (MsgID " << reqMessage.MessageID << ")");
-
-  // Check if dataset is announced correctly
-  if (reqMessage.DataSetType == DIMSE_DATASET_NULL)
-  {
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
-    DCMNET_ERROR("Received C-FIND request but no dataset announced, aborting");
-    return DIMSE_BADMESSAGE;
-  }
-
-  // Receive dataset
-  cond = receiveDIMSEDataset(&presIDdset, &dataset);
-  if (cond.bad())
-  {
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
-    DCMNET_ERROR("Unable to receive C-FIND dataset on presentation context " << OFstatic_cast(unsigned int, presID));
-    return DIMSE_BADDATA;
-  }
-
-  // Output request message only if trace level is enabled
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, dataset, presID));
-  else
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+                                       DcmDataset*& reqDataset)
+{
+    // Do some basic validity checks
+    if (m_assoc == NULL)
+        return DIMSE_ILLEGALASSOCIATION;
 
-  // Compare presentation context ID of command and data set
-  if (presIDdset != presID)
-  {
-    DCMNET_ERROR("Presentation Context ID of command (" << OFstatic_cast(unsigned int, presID)
-      << ") and data set (" << OFstatic_cast(unsigned int, presIDdset) << ") differs");
-    delete dataset;
-    return makeDcmnetCondition(DIMSEC_INVALIDPRESENTATIONCONTEXTID, OF_error,
-      "DIMSE: Presentation Contexts of Command and Data Set differ");
-  }
+    OFCondition cond;
+    OFString tempStr;
+    T_ASC_PresentationContextID presIDdset;
+    DcmDataset* dataset = NULL;
 
-  // Set return value
-  reqDataset = dataset;
+    // Dump debug information
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+        DCMNET_INFO("Received C-FIND Request");
+    else
+        DCMNET_INFO("Received C-FIND Request (MsgID " << reqMessage.MessageID << ")");
 
-  return cond;
-}
+    // Check if dataset is announced correctly
+    if (reqMessage.DataSetType == DIMSE_DATASET_NULL)
+    {
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+        DCMNET_ERROR("Received C-FIND request but no dataset announced, aborting");
+        return DIMSE_BADMESSAGE;
+    }
+
+    // Receive dataset
+    cond = receiveDIMSEDataset(&presIDdset, &dataset);
+    if (cond.bad())
+    {
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+        DCMNET_ERROR("Unable to receive C-FIND dataset on presentation context "
+                     << OFstatic_cast(unsigned int, presID));
+        return DIMSE_BADDATA;
+    }
 
+    // Output request message only if trace level is enabled
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, dataset, presID));
+    else
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+
+    // Compare presentation context ID of command and data set
+    if (presIDdset != presID)
+    {
+        DCMNET_ERROR("Presentation Context ID of command (" << OFstatic_cast(unsigned int, presID) << ") and data set ("
+                                                            << OFstatic_cast(unsigned int, presIDdset) << ") differs");
+        delete dataset;
+        return makeDcmnetCondition(DIMSEC_INVALIDPRESENTATIONCONTEXTID,
+                                   OF_error,
+                                   "DIMSE: Presentation Contexts of Command and Data Set differ");
+    }
+
+    // Set return value
+    reqDataset = dataset;
+
+    return cond;
+}
 
 OFCondition DcmSCP::sendFINDResponse(const T_ASC_PresentationContextID presID,
                                      const Uint16 messageID,
-                                     const OFString &sopClassUID,
-                                     DcmDataset *rspDataset,
+                                     const OFStringsopClassUID,
+                                     DcmDatasetrspDataset,
                                      const Uint16 rspStatusCode,
                                      DcmDataset* statusDetail)
 {
-  OFCondition cond;
-  OFString tempStr;
-
-  // Send back response
-  T_DIMSE_Message response;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&response, sizeof(response));
-  T_DIMSE_C_FindRSP &findRsp = response.msg.CFindRSP;
-  response.CommandField = DIMSE_C_FIND_RSP;
-  findRsp.MessageIDBeingRespondedTo = messageID;
-  findRsp.DimseStatus = rspStatusCode;
-  // Always send (the optional) field "Affected SOP Class UID"
-  findRsp.opts = O_FIND_AFFECTEDSOPCLASSUID;
-  OFStandard::strlcpy(findRsp.AffectedSOPClassUID, sopClassUID.c_str(), sizeof(findRsp.AffectedSOPClassUID));
-
-  if (rspDataset)
-    findRsp.DataSetType = DIMSE_DATASET_PRESENT;
-  else
-    findRsp.DataSetType = DIMSE_DATASET_NULL;
-
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-  {
-    DCMNET_INFO("Sending C-FIND Response");
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_OUTGOING, rspDataset, presID));
-  } else {
-    DCMNET_INFO("Sending C-FIND Response (" << DU_cfindStatusString(rspStatusCode) << ")");
-  }
-
-  // Send response message with dataset
-  cond = sendDIMSEMessage(presID, &response, rspDataset /* dataObject */, statusDetail);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed sending C-FIND response: " << DimseCondition::dump(tempStr, cond));
+    OFCondition cond;
+    OFString tempStr;
+
+    // Send back response
+    T_DIMSE_Message response;
+    // Make sure everything is zeroed (especially options)
+    bzero((char*)&response, sizeof(response));
+    T_DIMSE_C_FindRSP& findRsp        = response.msg.CFindRSP;
+    response.CommandField             = DIMSE_C_FIND_RSP;
+    findRsp.MessageIDBeingRespondedTo = messageID;
+    findRsp.DimseStatus               = rspStatusCode;
+    // Always send (the optional) field "Affected SOP Class UID"
+    findRsp.opts = O_FIND_AFFECTEDSOPCLASSUID;
+    OFStandard::strlcpy(findRsp.AffectedSOPClassUID, sopClassUID.c_str(), sizeof(findRsp.AffectedSOPClassUID));
+
+    if (rspDataset)
+        findRsp.DataSetType = DIMSE_DATASET_PRESENT;
+    else
+        findRsp.DataSetType = DIMSE_DATASET_NULL;
+
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+    {
+        DCMNET_INFO("Sending C-FIND Response");
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_OUTGOING, rspDataset, presID));
+    }
+    else
+    {
+        DCMNET_INFO("Sending C-FIND Response (" << DU_cfindStatusString(rspStatusCode) << ")");
+    }
+
+    // Send response message with dataset
+    cond = sendDIMSEMessage(presID, &response, rspDataset /* dataObject */, statusDetail);
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Failed sending C-FIND response: " << DimseCondition::dump(tempStr, cond));
+        return cond;
+    }
     return cond;
-  }
-  return cond;
 }
 
-
-OFCondition DcmSCP::checkForCANCEL(T_ASC_PresentationContextID presID,
-                                   const Uint16 messageID)
+OFCondition DcmSCP::checkForCANCEL(T_ASC_PresentationContextID presID, const Uint16 messageID)
 {
-  return DIMSE_checkForCancelRQ(m_assoc, presID, messageID);
+    return DIMSE_checkForCancelRQ(m_assoc, presID, messageID);
 }
 
 // ----------------------------------------------------------------------------
 
 // -- C-MOVE --
 
-OFCondition DcmSCP::receiveMOVERequest(T_DIMSE_C_MoveRQ &reqMessage,
+OFCondition DcmSCP::receiveMOVERequest(T_DIMSE_C_MoveRQreqMessage,
                                        const T_ASC_PresentationContextID presID,
-                                       DcmDataset *&reqDataset,
-                                       OFString &moveDest)
-{
-  // Do some basic validity checks
-  if (m_assoc == NULL)
-    return DIMSE_ILLEGALASSOCIATION;
-
-  OFCondition cond;
-  OFString tempStr;
-  T_ASC_PresentationContextID presIDdset;
-  DcmDataset *dataset = NULL;
-
-  // Dump debug information
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-    DCMNET_INFO("Received C-MOVE Request");
-  else
-    DCMNET_INFO("Received C-MOVE Request (MsgID " << reqMessage.MessageID << ")");
-
-  // Check if dataset is announced correctly
-  if (reqMessage.DataSetType == DIMSE_DATASET_NULL)
-  {
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
-    DCMNET_ERROR("Received C-MOVE request but no dataset announced, aborting");
-    return DIMSE_BADMESSAGE;
-  }
-
-  // Receive dataset
-  cond = receiveDIMSEDataset(&presIDdset, &dataset);
-  if (cond.bad())
-  {
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
-    DCMNET_ERROR("Unable to receive C-MOVE dataset on presentation context " << OFstatic_cast(unsigned int, presID));
-    return DIMSE_BADDATA;
-  }
-
-  // Output request message only if trace level is enabled
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, dataset, presID));
-  else
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+                                       DcmDataset*& reqDataset,
+                                       OFString& moveDest)
+{
+    // Do some basic validity checks
+    if (m_assoc == NULL)
+        return DIMSE_ILLEGALASSOCIATION;
 
-  // Compare presentation context ID of command and data set
-  if (presIDdset != presID)
-  {
-    DCMNET_ERROR("Presentation Context ID of command (" << OFstatic_cast(unsigned int, presID)
-      << ") and data set (" << OFstatic_cast(unsigned int, presIDdset) << ") differs");
-    delete dataset;
-    return makeDcmnetCondition(DIMSEC_INVALIDPRESENTATIONCONTEXTID, OF_error,
-      "DIMSE: Presentation Contexts of Command and Data Set differ");
-  }
+    OFCondition cond;
+    OFString tempStr;
+    T_ASC_PresentationContextID presIDdset;
+    DcmDataset* dataset = NULL;
 
-  // Set return values
-  reqDataset = dataset;
-  moveDest = reqMessage.MoveDestination;
+    // Dump debug information
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+        DCMNET_INFO("Received C-MOVE Request");
+    else
+        DCMNET_INFO("Received C-MOVE Request (MsgID " << reqMessage.MessageID << ")");
 
-  return cond;
-}
+    // Check if dataset is announced correctly
+    if (reqMessage.DataSetType == DIMSE_DATASET_NULL)
+    {
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+        DCMNET_ERROR("Received C-MOVE request but no dataset announced, aborting");
+        return DIMSE_BADMESSAGE;
+    }
+
+    // Receive dataset
+    cond = receiveDIMSEDataset(&presIDdset, &dataset);
+    if (cond.bad())
+    {
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+        DCMNET_ERROR("Unable to receive C-MOVE dataset on presentation context "
+                     << OFstatic_cast(unsigned int, presID));
+        return DIMSE_BADDATA;
+    }
 
+    // Output request message only if trace level is enabled
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, dataset, presID));
+    else
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+
+    // Compare presentation context ID of command and data set
+    if (presIDdset != presID)
+    {
+        DCMNET_ERROR("Presentation Context ID of command (" << OFstatic_cast(unsigned int, presID) << ") and data set ("
+                                                            << OFstatic_cast(unsigned int, presIDdset) << ") differs");
+        delete dataset;
+        return makeDcmnetCondition(DIMSEC_INVALIDPRESENTATIONCONTEXTID,
+                                   OF_error,
+                                   "DIMSE: Presentation Contexts of Command and Data Set differ");
+    }
+
+    // Set return values
+    reqDataset = dataset;
+    moveDest   = reqMessage.MoveDestination;
+
+    return cond;
+}
 
 OFCondition DcmSCP::sendMOVEResponse(const T_ASC_PresentationContextID presID,
                                      const Uint16 messageID,
-                                     const OFString &sopClassUID,
-                                     DcmDataset *rspDataset,
+                                     const OFStringsopClassUID,
+                                     DcmDatasetrspDataset,
                                      const Uint16 rspStatusCode,
-                                     DcmDataset *statusDetail,
+                                     DcmDatasetstatusDetail,
                                      const Uint16 numRemain,
                                      const Uint16 numComplete,
                                      const Uint16 numFail,
                                      const Uint16 numWarn)
 {
-  OFCondition cond;
-  OFString tempStr;
-
-  // Send back response
-  T_DIMSE_Message response;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&response, sizeof(response));
-  T_DIMSE_C_MoveRSP &moveRsp = response.msg.CMoveRSP;
-  response.CommandField = DIMSE_C_MOVE_RSP;
-  moveRsp.MessageIDBeingRespondedTo = messageID;
-  moveRsp.DimseStatus = rspStatusCode;
-  // Always send the optional field "Affected SOP Class UID"
-  moveRsp.opts = O_MOVE_AFFECTEDSOPCLASSUID;
-  OFStandard::strlcpy(moveRsp.AffectedSOPClassUID, sopClassUID.c_str(), sizeof(moveRsp.AffectedSOPClassUID));
-  // Only send the other optional fields if needed
-  if ( (numRemain != 0) || (numComplete != 0) || (numFail != 0) || (numWarn != 0) )
-  {
-    moveRsp.NumberOfRemainingSubOperations = numRemain;
-    moveRsp.NumberOfCompletedSubOperations = numComplete;
-    moveRsp.NumberOfFailedSubOperations = numFail;
-    moveRsp.NumberOfWarningSubOperations = numWarn;
-    moveRsp.opts |= O_MOVE_NUMBEROFREMAININGSUBOPERATIONS | O_MOVE_NUMBEROFCOMPLETEDSUBOPERATIONS |
-                    O_MOVE_NUMBEROFFAILEDSUBOPERATIONS | O_MOVE_NUMBEROFWARNINGSUBOPERATIONS;
-  }
-
-  if (rspDataset)
-    moveRsp.DataSetType = DIMSE_DATASET_PRESENT;
-  else
-    moveRsp.DataSetType = DIMSE_DATASET_NULL;
-
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-  {
-    DCMNET_INFO("Sending C-MOVE Response");
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_OUTGOING, rspDataset, presID));
-  } else {
-    DCMNET_INFO("Sending C-MOVE Response (" << DU_cmoveStatusString(rspStatusCode) << ")");
-  }
-
-  // Send response message with dataset
-  cond = sendDIMSEMessage(presID, &response, rspDataset /* dataObject */, statusDetail);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed sending C-MOVE response: " << DimseCondition::dump(tempStr, cond));
-  }
+    OFCondition cond;
+    OFString tempStr;
 
-  return cond;
+    // Send back response
+    T_DIMSE_Message response;
+    // Make sure everything is zeroed (especially options)
+    bzero((char*)&response, sizeof(response));
+    T_DIMSE_C_MoveRSP& moveRsp        = response.msg.CMoveRSP;
+    response.CommandField             = DIMSE_C_MOVE_RSP;
+    moveRsp.MessageIDBeingRespondedTo = messageID;
+    moveRsp.DimseStatus               = rspStatusCode;
+    // Always send the optional field "Affected SOP Class UID"
+    moveRsp.opts = O_MOVE_AFFECTEDSOPCLASSUID;
+    OFStandard::strlcpy(moveRsp.AffectedSOPClassUID, sopClassUID.c_str(), sizeof(moveRsp.AffectedSOPClassUID));
+    // Only send the other optional fields if needed
+    if ((numRemain != 0) || (numComplete != 0) || (numFail != 0) || (numWarn != 0))
+    {
+        moveRsp.NumberOfRemainingSubOperations = numRemain;
+        moveRsp.NumberOfCompletedSubOperations = numComplete;
+        moveRsp.NumberOfFailedSubOperations    = numFail;
+        moveRsp.NumberOfWarningSubOperations   = numWarn;
+        moveRsp.opts |= O_MOVE_NUMBEROFREMAININGSUBOPERATIONS | O_MOVE_NUMBEROFCOMPLETEDSUBOPERATIONS
+            | O_MOVE_NUMBEROFFAILEDSUBOPERATIONS | O_MOVE_NUMBEROFWARNINGSUBOPERATIONS;
+    }
+
+    if (rspDataset)
+        moveRsp.DataSetType = DIMSE_DATASET_PRESENT;
+    else
+        moveRsp.DataSetType = DIMSE_DATASET_NULL;
+
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+    {
+        DCMNET_INFO("Sending C-MOVE Response");
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_OUTGOING, rspDataset, presID));
+    }
+    else
+    {
+        DCMNET_INFO("Sending C-MOVE Response (" << DU_cmoveStatusString(rspStatusCode) << ")");
+    }
+
+    // Send response message with dataset
+    cond = sendDIMSEMessage(presID, &response, rspDataset /* dataObject */, statusDetail);
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Failed sending C-MOVE response: " << DimseCondition::dump(tempStr, cond));
+    }
+
+    return cond;
 }
 
 // ----------------------------------------------------------------------------
 
 // -- N-ACTION --
 
-OFCondition DcmSCP::receiveACTIONRequest(T_DIMSE_N_ActionRQ &reqMessage,
+OFCondition DcmSCP::receiveACTIONRequest(T_DIMSE_N_ActionRQreqMessage,
                                          const T_ASC_PresentationContextID presID,
-                                         DcmDataset *&reqDataset,
-                                         Uint16 &actionTypeID)
-{
-  // Do some basic validity checks
-  if (m_assoc == NULL)
-    return DIMSE_ILLEGALASSOCIATION;
-
-  OFCondition cond;
-  OFString tempStr;
-  T_ASC_PresentationContextID presIDdset;
-  DcmDataset *dataset = NULL;
-
-  // Dump debug information
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-    DCMNET_INFO("Received N-ACTION Request");
-  else
-    DCMNET_INFO("Received N-ACTION Request (MsgID " << reqMessage.MessageID << ")");
-
-  // Check if dataset is announced correctly
-  if (reqMessage.DataSetType == DIMSE_DATASET_NULL)
-  {
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
-    DCMNET_ERROR("Received N-ACTION request but no dataset announced, aborting");
-    return DIMSE_BADMESSAGE;
-  }
-
-  // Receive dataset
-  cond = receiveDIMSEDataset(&presIDdset, &dataset);
-  if (cond.bad())
-  {
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
-    DCMNET_ERROR("Unable to receive N-ACTION dataset on presentation context " << OFstatic_cast(unsigned int, presID));
-    return DIMSE_BADDATA;
-  }
-
-  // Output request message only if trace level is enabled
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, dataset, presID));
-  else
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+                                         DcmDataset*& reqDataset,
+                                         Uint16& actionTypeID)
+{
+    // Do some basic validity checks
+    if (m_assoc == NULL)
+        return DIMSE_ILLEGALASSOCIATION;
+
+    OFCondition cond;
+    OFString tempStr;
+    T_ASC_PresentationContextID presIDdset;
+    DcmDataset* dataset = NULL;
 
-  // Compare presentation context ID of command and data set
-  if (presIDdset != presID)
-  {
-    DCMNET_ERROR("Presentation Context ID of command (" << OFstatic_cast(unsigned int, presID)
-      << ") and data set (" << OFstatic_cast(unsigned int, presIDdset) << ") differs");
-    delete dataset;
-    return makeDcmnetCondition(DIMSEC_INVALIDPRESENTATIONCONTEXTID, OF_error,
-      "DIMSE: Presentation Contexts of Command and Data Set differ");
-  }
+    // Dump debug information
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+        DCMNET_INFO("Received N-ACTION Request");
+    else
+        DCMNET_INFO("Received N-ACTION Request (MsgID " << reqMessage.MessageID << ")");
 
-  // Set return values
-  reqDataset = dataset;
-  actionTypeID = reqMessage.ActionTypeID;
+    // Check if dataset is announced correctly
+    if (reqMessage.DataSetType == DIMSE_DATASET_NULL)
+    {
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+        DCMNET_ERROR("Received N-ACTION request but no dataset announced, aborting");
+        return DIMSE_BADMESSAGE;
+    }
 
-  return cond;
-}
+    // Receive dataset
+    cond = receiveDIMSEDataset(&presIDdset, &dataset);
+    if (cond.bad())
+    {
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+        DCMNET_ERROR("Unable to receive N-ACTION dataset on presentation context "
+                     << OFstatic_cast(unsigned int, presID));
+        return DIMSE_BADDATA;
+    }
+
+    // Output request message only if trace level is enabled
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, dataset, presID));
+    else
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+
+    // Compare presentation context ID of command and data set
+    if (presIDdset != presID)
+    {
+        DCMNET_ERROR("Presentation Context ID of command (" << OFstatic_cast(unsigned int, presID) << ") and data set ("
+                                                            << OFstatic_cast(unsigned int, presIDdset) << ") differs");
+        delete dataset;
+        return makeDcmnetCondition(DIMSEC_INVALIDPRESENTATIONCONTEXTID,
+                                   OF_error,
+                                   "DIMSE: Presentation Contexts of Command and Data Set differ");
+    }
+
+    // Set return values
+    reqDataset   = dataset;
+    actionTypeID = reqMessage.ActionTypeID;
 
+    return cond;
+}
 
 OFCondition DcmSCP::sendACTIONResponse(const T_ASC_PresentationContextID presID,
                                        const Uint16 messageID,
-                                       const OFString &sopClassUID,
-                                       const OFString &sopInstanceUID,
+                                       const OFStringsopClassUID,
+                                       const OFStringsopInstanceUID,
                                        const Uint16 rspStatusCode)
 {
-  OFCondition cond;
-  OFString tempStr;
-
-  // Send back response
-  T_DIMSE_Message response;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&response, sizeof(response));
-  T_DIMSE_N_ActionRSP &actionRsp = response.msg.NActionRSP;
-  response.CommandField = DIMSE_N_ACTION_RSP;
-  actionRsp.MessageIDBeingRespondedTo = messageID;
-  actionRsp.DimseStatus = rspStatusCode;
-  actionRsp.DataSetType = DIMSE_DATASET_NULL;
-  // Always send the optional fields "Affected SOP Class UID" and "Affected SOP Instance UID"
-  actionRsp.opts = O_NACTION_AFFECTEDSOPCLASSUID | O_NACTION_AFFECTEDSOPINSTANCEUID;
-  OFStandard::strlcpy(actionRsp.AffectedSOPClassUID, sopClassUID.c_str(), sizeof(actionRsp.AffectedSOPClassUID));
-  OFStandard::strlcpy(actionRsp.AffectedSOPInstanceUID, sopInstanceUID.c_str(), sizeof(actionRsp.AffectedSOPInstanceUID));
-  // Do not send any other optional fields, e.g. "Action Type ID"
-
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-  {
-    DCMNET_INFO("Sending N-ACTION Response");
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_OUTGOING, NULL, presID));
-  } else {
-    DCMNET_INFO("Sending N-ACTION Response (" << DU_nactionStatusString(rspStatusCode) << ")");
-  }
-
-  // Send response message
-  cond = sendDIMSEMessage(presID, &response, NULL /* dataObject */);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed sending N-ACTION response: " << DimseCondition::dump(tempStr, cond));
-  }
+    OFCondition cond;
+    OFString tempStr;
 
-  return cond;
+    // Send back response
+    T_DIMSE_Message response;
+    // Make sure everything is zeroed (especially options)
+    bzero((char*)&response, sizeof(response));
+    T_DIMSE_N_ActionRSP& actionRsp      = response.msg.NActionRSP;
+    response.CommandField               = DIMSE_N_ACTION_RSP;
+    actionRsp.MessageIDBeingRespondedTo = messageID;
+    actionRsp.DimseStatus               = rspStatusCode;
+    actionRsp.DataSetType               = DIMSE_DATASET_NULL;
+    // Always send the optional fields "Affected SOP Class UID" and "Affected SOP Instance UID"
+    actionRsp.opts = O_NACTION_AFFECTEDSOPCLASSUID | O_NACTION_AFFECTEDSOPINSTANCEUID;
+    OFStandard::strlcpy(actionRsp.AffectedSOPClassUID, sopClassUID.c_str(), sizeof(actionRsp.AffectedSOPClassUID));
+    OFStandard::strlcpy(
+        actionRsp.AffectedSOPInstanceUID, sopInstanceUID.c_str(), sizeof(actionRsp.AffectedSOPInstanceUID));
+    // Do not send any other optional fields, e.g. "Action Type ID"
+
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+    {
+        DCMNET_INFO("Sending N-ACTION Response");
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_OUTGOING, NULL, presID));
+    }
+    else
+    {
+        DCMNET_INFO("Sending N-ACTION Response (" << DU_nactionStatusString(rspStatusCode) << ")");
+    }
+
+    // Send response message
+    cond = sendDIMSEMessage(presID, &response, NULL /* dataObject */);
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Failed sending N-ACTION response: " << DimseCondition::dump(tempStr, cond));
+    }
+
+    return cond;
 }
 
 // ----------------------------------------------------------------------------
 
 // -- N-EVENT-REPORT --
 
-OFCondition DcmSCP::handleEVENTREPORTRequest(T_DIMSE_N_EventReportRQ &reqMessage,
+OFCondition DcmSCP::handleEVENTREPORTRequest(T_DIMSE_N_EventReportRQreqMessage,
                                              const T_ASC_PresentationContextID presID,
-                                             DcmDataset *&reqDataset,
-                                             Uint16 &eventTypeID)
-{
-  // Do some basic validity checks
-  if (m_assoc == NULL)
-    return DIMSE_ILLEGALASSOCIATION;
-
-  OFCondition cond;
-  OFString tempStr;
-  T_ASC_PresentationContextID presIDdset;
-  DcmDataset *dataset = NULL;
-  // DcmDataset *statusDetail = NULL; // TODO: do we need this and if so, how do we get it?
-  Uint16 rspStatusCode = 0;
-
-  // Dump debug information
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
-    DCMNET_INFO("Received N-EVENT-REPORT Request");
-  else
-    DCMNET_INFO("Received N-EVENT-REPORT Request (MsgID " << reqMessage.MessageID << ")");
-
-  // Check if dataset is announced correctly
-  if (reqMessage.DataSetType == DIMSE_DATASET_NULL)
-  {
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
-    DCMNET_ERROR("Received N-EVENT-REPORT request but no dataset announced, aborting");
-    return DIMSE_BADMESSAGE;
-  }
-
-  // Receive dataset
-  cond = receiveDIMSEDataset(&presIDdset, &dataset);
-  if (cond.bad())
-  {
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
-    DCMNET_ERROR("Unable to receive N-EVENT-REPORT dataset on presentation context " << OFstatic_cast(unsigned int, presID));
-    return DIMSE_BADDATA;
-  }
-
-  // Output dataset only if trace level is enabled
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, dataset, presID));
-  else
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+                                             DcmDataset*& reqDataset,
+                                             Uint16& eventTypeID)
+{
+    // Do some basic validity checks
+    if (m_assoc == NULL)
+        return DIMSE_ILLEGALASSOCIATION;
 
-  // Compare presentation context ID of command and data set
-  if (presIDdset != presID)
-  {
-    DCMNET_ERROR("Presentation Context ID of command (" << OFstatic_cast(unsigned int, presID)
-      << ") and data set (" << OFstatic_cast(unsigned int, presIDdset) << ") differs");
-    delete dataset;
-    return makeDcmnetCondition(DIMSEC_INVALIDPRESENTATIONCONTEXTID, OF_error,
-      "DIMSE: Presentation Contexts of Command and Data Set differ");
-  }
-
-  // Check the request message and dataset and return the DIMSE status code to be used
-  rspStatusCode = checkEVENTREPORTRequest(reqMessage, dataset);
-
-  // Send back response
-  T_DIMSE_Message response;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&response, sizeof(response));
-  T_DIMSE_N_EventReportRSP &eventReportRsp = response.msg.NEventReportRSP;
-  response.CommandField = DIMSE_N_EVENT_REPORT_RSP;
-  eventReportRsp.MessageIDBeingRespondedTo = reqMessage.MessageID;
-  eventReportRsp.DimseStatus = rspStatusCode;
-  eventReportRsp.DataSetType = DIMSE_DATASET_NULL;
-  // Do not send any optional fields
-  eventReportRsp.opts = 0;
-  eventReportRsp.AffectedSOPClassUID[0] = 0;
-  eventReportRsp.AffectedSOPInstanceUID[0] = 0;
-
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-  {
-    DCMNET_INFO("Sending N-EVENT-REPORT Response");
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_OUTGOING, NULL, presID));
-  } else {
-    DCMNET_INFO("Sending N-EVENT-REPORT Response (" << DU_neventReportStatusString(rspStatusCode) << ")");
-  }
-  // Send response message
-  cond = sendDIMSEMessage(presID, &response, NULL /* dataObject */);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed sending N-EVENT-REPORT response: " << DimseCondition::dump(tempStr, cond));
-    delete dataset;
-    return cond;
-  }
+    OFCondition cond;
+    OFString tempStr;
+    T_ASC_PresentationContextID presIDdset;
+    DcmDataset* dataset = NULL;
+    // DcmDataset *statusDetail = NULL; // TODO: do we need this and if so, how do we get it?
+    Uint16 rspStatusCode = 0;
 
-  // Set return values
-  reqDataset = dataset;
-  eventTypeID = reqMessage.EventTypeID;
+    // Dump debug information
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
+        DCMNET_INFO("Received N-EVENT-REPORT Request");
+    else
+        DCMNET_INFO("Received N-EVENT-REPORT Request (MsgID " << reqMessage.MessageID << ")");
 
-  return cond;
-}
+    // Check if dataset is announced correctly
+    if (reqMessage.DataSetType == DIMSE_DATASET_NULL)
+    {
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+        DCMNET_ERROR("Received N-EVENT-REPORT request but no dataset announced, aborting");
+        return DIMSE_BADMESSAGE;
+    }
 
+    // Receive dataset
+    cond = receiveDIMSEDataset(&presIDdset, &dataset);
+    if (cond.bad())
+    {
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+        DCMNET_ERROR("Unable to receive N-EVENT-REPORT dataset on presentation context "
+                     << OFstatic_cast(unsigned int, presID));
+        return DIMSE_BADDATA;
+    }
 
-OFCondition DcmSCP::sendEVENTREPORTRequest(const T_ASC_PresentationContextID presID,
-                                           const OFString &sopInstanceUID,
-                                           const Uint16 messageID,
-                                           const Uint16 eventTypeID,
-                                           DcmDataset *reqDataset,
-                                           Uint16 &rspStatusCode)
-{
-  // Do some basic validity checks
-  if (m_assoc == NULL)
-    return DIMSE_ILLEGALASSOCIATION;
-  if (sopInstanceUID.empty() || (reqDataset == NULL))
-    return DIMSE_NULLKEY;
-
-  // Prepare DIMSE data structures for issuing request
-  OFCondition cond;
-  OFString tempStr;
-  T_ASC_PresentationContextID pcid = presID;
-  T_DIMSE_Message request;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&request, sizeof(request));
-  T_DIMSE_N_EventReportRQ &eventReportReq = request.msg.NEventReportRQ;
-  DcmDataset *statusDetail = NULL;
-
-  request.CommandField = DIMSE_N_EVENT_REPORT_RQ;
-
-  // Generate a new message ID (?)
-  eventReportReq.MessageID = messageID;
-
-  eventReportReq.DataSetType = DIMSE_DATASET_PRESENT;
-  eventReportReq.EventTypeID = eventTypeID;
-
-  // Determine SOP Class from presentation context
-  OFString abstractSyntax, transferSyntax;
-
-  findPresentationContext(pcid, abstractSyntax, transferSyntax);
-  if (abstractSyntax.empty() || transferSyntax.empty())
-    return DIMSE_NOVALIDPRESENTATIONCONTEXTID;
-  OFStandard::strlcpy(eventReportReq.AffectedSOPClassUID, abstractSyntax.c_str(), sizeof(eventReportReq.AffectedSOPClassUID));
-  OFStandard::strlcpy(eventReportReq.AffectedSOPInstanceUID, sopInstanceUID.c_str(), sizeof(eventReportReq.AffectedSOPInstanceUID));
-
-  // Send request
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-  {
-    DCMNET_INFO("Sending N-EVENT-REPORT Request");
     // Output dataset only if trace level is enabled
     if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
-      DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_OUTGOING, reqDataset, pcid));
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, dataset, presID));
     else
-      DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_OUTGOING, NULL, pcid));
-  } else {
-    DCMNET_INFO("Sending N-EVENT-REPORT Request (MsgID " << eventReportReq.MessageID << ")");
-  }
-  cond = sendDIMSEMessage(pcid, &request, reqDataset);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed sending N-EVENT-REPORT request: " << DimseCondition::dump(tempStr, cond));
-    return cond;
-  }
-  // Receive response
-  T_DIMSE_Message response;
-  cond = receiveDIMSECommand(&pcid, &response, &statusDetail, NULL /* commandSet */);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed receiving DIMSE response: " << DimseCondition::dump(tempStr, cond));
-    return cond;
-  }
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, reqMessage, DIMSE_INCOMING, NULL, presID));
+
+    // Compare presentation context ID of command and data set
+    if (presIDdset != presID)
+    {
+        DCMNET_ERROR("Presentation Context ID of command (" << OFstatic_cast(unsigned int, presID) << ") and data set ("
+                                                            << OFstatic_cast(unsigned int, presIDdset) << ") differs");
+        delete dataset;
+        return makeDcmnetCondition(DIMSEC_INVALIDPRESENTATIONCONTEXTID,
+                                   OF_error,
+                                   "DIMSE: Presentation Contexts of Command and Data Set differ");
+    }
+
+    // Check the request message and dataset and return the DIMSE status code to be used
+    rspStatusCode = checkEVENTREPORTRequest(reqMessage, dataset);
+
+    // Send back response
+    T_DIMSE_Message response;
+    // Make sure everything is zeroed (especially options)
+    bzero((char*)&response, sizeof(response));
+    T_DIMSE_N_EventReportRSP& eventReportRsp = response.msg.NEventReportRSP;
+    response.CommandField                    = DIMSE_N_EVENT_REPORT_RSP;
+    eventReportRsp.MessageIDBeingRespondedTo = reqMessage.MessageID;
+    eventReportRsp.DimseStatus               = rspStatusCode;
+    eventReportRsp.DataSetType               = DIMSE_DATASET_NULL;
+    // Do not send any optional fields
+    eventReportRsp.opts                      = 0;
+    eventReportRsp.AffectedSOPClassUID[0]    = 0;
+    eventReportRsp.AffectedSOPInstanceUID[0] = 0;
 
-  // Check command set
-  if (response.CommandField == DIMSE_N_EVENT_REPORT_RSP)
-  {
     if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
     {
-      DCMNET_INFO("Received N-EVENT-REPORT Response");
-      DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_INCOMING, NULL, pcid));
-    } else {
-      DCMNET_INFO("Received N-EVENT-REPORT Response (" << DU_neventReportStatusString(response.msg.NEventReportRSP.DimseStatus) << ")");
-    }
-  } else {
-    DCMNET_ERROR("Expected N-EVENT-REPORT response but received DIMSE command 0x"
-        << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
-        << OFstatic_cast(unsigned int, response.CommandField));
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_INCOMING, NULL, pcid));
-    delete statusDetail;
-    return DIMSE_BADCOMMANDTYPE;
-  }
-  if (statusDetail != NULL)
-  {
-    DCMNET_DEBUG("Response has status detail:" << OFendl << DcmObject::PrintHelper(*statusDetail));
-    delete statusDetail;
-  }
-
-  // Set return value
-  T_DIMSE_N_EventReportRSP &eventReportRsp = response.msg.NEventReportRSP;
-  rspStatusCode = eventReportRsp.DimseStatus;
-
-  // Check whether there is a dataset to be received
-  if (eventReportRsp.DataSetType == DIMSE_DATASET_PRESENT)
-  {
-    // this should never happen
-    DcmDataset *tempDataset = NULL;
-    T_ASC_PresentationContextID tempID;
-    // Receive dataset
-    cond = receiveDIMSEDataset(&tempID, &tempDataset);
-    if (cond.good())
+        DCMNET_INFO("Sending N-EVENT-REPORT Response");
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_OUTGOING, NULL, presID));
+    }
+    else
     {
-      DCMNET_WARN("Received unexpected dataset after N-EVENT-REPORT response, ignoring");
-      delete tempDataset;
-    } else {
-      DCMNET_ERROR("Failed receiving unexpected dataset after N-EVENT-REPORT response: "
-        << DimseCondition::dump(tempStr, cond));
-      return DIMSE_BADDATA;
+        DCMNET_INFO("Sending N-EVENT-REPORT Response (" << DU_neventReportStatusString(rspStatusCode) << ")");
+    }
+    // Send response message
+    cond = sendDIMSEMessage(presID, &response, NULL /* dataObject */);
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Failed sending N-EVENT-REPORT response: " << DimseCondition::dump(tempStr, cond));
+        delete dataset;
+        return cond;
     }
-  }
 
-  // Check whether the message ID being responded to is equal to the message ID of the request
-  if (eventReportRsp.MessageIDBeingRespondedTo != eventReportReq.MessageID)
-  {
-    DCMNET_ERROR("Received response with wrong message ID (" << eventReportRsp.MessageIDBeingRespondedTo
-      << " instead of " << eventReportReq.MessageID << ")");
-    return DIMSE_BADMESSAGE;
-  }
+    // Set return values
+    reqDataset  = dataset;
+    eventTypeID = reqMessage.EventTypeID;
 
-  return cond;
+    return cond;
 }
 
-
-Uint16 DcmSCP::checkEVENTREPORTRequest(T_DIMSE_N_EventReportRQ & /*reqMessage*/,
-                                       DcmDataset * /*reqDataset*/)
+OFCondition DcmSCP::sendEVENTREPORTRequest(const T_ASC_PresentationContextID presID,
+                                           const OFString& sopInstanceUID,
+                                           const Uint16 messageID,
+                                           const Uint16 eventTypeID,
+                                           DcmDataset* reqDataset,
+                                           Uint16& rspStatusCode)
 {
-  // we default to success
-  return STATUS_Success;
+    // Do some basic validity checks
+    if (m_assoc == NULL)
+        return DIMSE_ILLEGALASSOCIATION;
+    if (sopInstanceUID.empty() || (reqDataset == NULL))
+        return DIMSE_NULLKEY;
+
+    // Prepare DIMSE data structures for issuing request
+    OFCondition cond;
+    OFString tempStr;
+    T_ASC_PresentationContextID pcid = presID;
+    T_DIMSE_Message request;
+    // Make sure everything is zeroed (especially options)
+    bzero((char*)&request, sizeof(request));
+    T_DIMSE_N_EventReportRQ& eventReportReq = request.msg.NEventReportRQ;
+    DcmDataset* statusDetail                = NULL;
+
+    request.CommandField = DIMSE_N_EVENT_REPORT_RQ;
+
+    // Generate a new message ID (?)
+    eventReportReq.MessageID = messageID;
+
+    eventReportReq.DataSetType = DIMSE_DATASET_PRESENT;
+    eventReportReq.EventTypeID = eventTypeID;
+
+    // Determine SOP Class from presentation context
+    OFString abstractSyntax, transferSyntax;
+
+    findPresentationContext(pcid, abstractSyntax, transferSyntax);
+    if (abstractSyntax.empty() || transferSyntax.empty())
+        return DIMSE_NOVALIDPRESENTATIONCONTEXTID;
+    OFStandard::strlcpy(
+        eventReportReq.AffectedSOPClassUID, abstractSyntax.c_str(), sizeof(eventReportReq.AffectedSOPClassUID));
+    OFStandard::strlcpy(
+        eventReportReq.AffectedSOPInstanceUID, sopInstanceUID.c_str(), sizeof(eventReportReq.AffectedSOPInstanceUID));
+
+    // Send request
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+    {
+        DCMNET_INFO("Sending N-EVENT-REPORT Request");
+        // Output dataset only if trace level is enabled
+        if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
+            DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_OUTGOING, reqDataset, pcid));
+        else
+            DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_OUTGOING, NULL, pcid));
+    }
+    else
+    {
+        DCMNET_INFO("Sending N-EVENT-REPORT Request (MsgID " << eventReportReq.MessageID << ")");
+    }
+    cond = sendDIMSEMessage(pcid, &request, reqDataset);
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Failed sending N-EVENT-REPORT request: " << DimseCondition::dump(tempStr, cond));
+        return cond;
+    }
+    // Receive response
+    T_DIMSE_Message response;
+    cond = receiveDIMSECommand(&pcid, &response, &statusDetail, NULL /* commandSet */);
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Failed receiving DIMSE response: " << DimseCondition::dump(tempStr, cond));
+        return cond;
+    }
+
+    // Check command set
+    if (response.CommandField == DIMSE_N_EVENT_REPORT_RSP)
+    {
+        if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+        {
+            DCMNET_INFO("Received N-EVENT-REPORT Response");
+            DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_INCOMING, NULL, pcid));
+        }
+        else
+        {
+            DCMNET_INFO("Received N-EVENT-REPORT Response ("
+                        << DU_neventReportStatusString(response.msg.NEventReportRSP.DimseStatus) << ")");
+        }
+    }
+    else
+    {
+        DCMNET_ERROR("Expected N-EVENT-REPORT response but received DIMSE command 0x"
+                     << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
+                     << OFstatic_cast(unsigned int, response.CommandField));
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_INCOMING, NULL, pcid));
+        delete statusDetail;
+        return DIMSE_BADCOMMANDTYPE;
+    }
+    if (statusDetail != NULL)
+    {
+        DCMNET_DEBUG("Response has status detail:" << OFendl << DcmObject::PrintHelper(*statusDetail));
+        delete statusDetail;
+    }
+
+    // Set return value
+    T_DIMSE_N_EventReportRSP& eventReportRsp = response.msg.NEventReportRSP;
+    rspStatusCode                            = eventReportRsp.DimseStatus;
+
+    // Check whether there is a dataset to be received
+    if (eventReportRsp.DataSetType == DIMSE_DATASET_PRESENT)
+    {
+        // this should never happen
+        DcmDataset* tempDataset = NULL;
+        T_ASC_PresentationContextID tempID;
+        // Receive dataset
+        cond = receiveDIMSEDataset(&tempID, &tempDataset);
+        if (cond.good())
+        {
+            DCMNET_WARN("Received unexpected dataset after N-EVENT-REPORT response, ignoring");
+            delete tempDataset;
+        }
+        else
+        {
+            DCMNET_ERROR("Failed receiving unexpected dataset after N-EVENT-REPORT response: "
+                         << DimseCondition::dump(tempStr, cond));
+            return DIMSE_BADDATA;
+        }
+    }
+
+    // Check whether the message ID being responded to is equal to the message ID of the request
+    if (eventReportRsp.MessageIDBeingRespondedTo != eventReportReq.MessageID)
+    {
+        DCMNET_ERROR("Received response with wrong message ID (" << eventReportRsp.MessageIDBeingRespondedTo
+                                                                 << " instead of " << eventReportReq.MessageID << ")");
+        return DIMSE_BADMESSAGE;
+    }
+
+    return cond;
 }
 
+Uint16 DcmSCP::checkEVENTREPORTRequest(T_DIMSE_N_EventReportRQ& /*reqMessage*/, DcmDataset* /*reqDataset*/)
+{
+    // we default to success
+    return STATUS_Success;
+}
 
 /* ************************************************************************* */
 /*                         General message handling                          */
@@ -1412,366 +1496,406 @@ Uint16 DcmSCP::checkEVENTREPORTRequest(T_DIMSE_N_EventReportRQ & /*reqMessage*/,
 
 void DcmSCP::notifySENDProgress(const unsigned long byteCount)
 {
-  DCMNET_TRACE("Bytes sent: " << byteCount);
+    DCMNET_TRACE("Bytes sent: " << byteCount);
 }
 
-
 void DcmSCP::notifyRECEIVEProgress(const unsigned long byteCount)
 {
-  DCMNET_TRACE("Bytes received: " << byteCount);
+    DCMNET_TRACE("Bytes received: " << byteCount);
 }
 
-
 /* ************************************************************************* */
 /*                            Various helpers                                */
 /* ************************************************************************* */
 
 // Sends a DIMSE command and possibly also instance data to the configured peer DICOM application
 OFCondition DcmSCP::sendDIMSEMessage(const T_ASC_PresentationContextID presID,
-                                     T_DIMSE_Message *message,
-                                     DcmDataset *dataObject,
-                                     DcmDataset *statusDetail,
-                                     DcmDataset **commandSet)
-{
-  if (m_assoc == NULL)
-    return DIMSE_ILLEGALASSOCIATION;
-  if (message == NULL)
-    return DIMSE_NULLKEY;
-
-  OFCondition cond;
-  /* call the corresponding DIMSE function to sent the message */
-  if (m_cfg->getProgressNotificationMode())
-  {
-    cond = DIMSE_sendMessageUsingMemoryData(m_assoc, presID, message, statusDetail, dataObject,
-                                            callbackSENDProgress, this /*callbackData*/, commandSet);
-  } else {
-    cond = DIMSE_sendMessageUsingMemoryData(m_assoc, presID, message, statusDetail, dataObject,
-                                            NULL /*callback*/, NULL /*callbackData*/, commandSet);
-  }
-  return cond;
+                                     T_DIMSE_Message* message,
+                                     DcmDataset* dataObject,
+                                     DcmDataset* statusDetail,
+                                     DcmDataset** commandSet)
+{
+    if (m_assoc == NULL)
+        return DIMSE_ILLEGALASSOCIATION;
+    if (message == NULL)
+        return DIMSE_NULLKEY;
+
+    OFCondition cond;
+    /* call the corresponding DIMSE function to sent the message */
+    if (m_cfg->getProgressNotificationMode())
+    {
+        cond = DIMSE_sendMessageUsingMemoryData(m_assoc,
+                                                presID,
+                                                message,
+                                                statusDetail,
+                                                dataObject,
+                                                callbackSENDProgress,
+                                                this /*callbackData*/,
+                                                commandSet);
+    }
+    else
+    {
+        cond = DIMSE_sendMessageUsingMemoryData(
+            m_assoc, presID, message, statusDetail, dataObject, NULL /*callback*/, NULL /*callbackData*/, commandSet);
+    }
+    return cond;
 }
 
 // ----------------------------------------------------------------------------
 
 // Receive DIMSE command (excluding dataset!) over the currently open association
-OFCondition DcmSCP::receiveDIMSECommand(T_ASC_PresentationContextID *presID,
-                                        T_DIMSE_Message *message,
-                                        DcmDataset **statusDetail,
-                                        DcmDataset **commandSet,
+OFCondition DcmSCP::receiveDIMSECommand(T_ASC_PresentationContextIDpresID,
+                                        T_DIMSE_Messagemessage,
+                                        DcmDataset** statusDetail,
+                                        DcmDataset** commandSet,
                                         const Uint32 timeout)
 {
-  if (m_assoc == NULL)
-    return DIMSE_ILLEGALASSOCIATION;
-
-  OFCondition cond;
-  if (timeout > 0)
-  {
-    /* call the corresponding DIMSE function to receive the command (use specified timeout) */
-    cond = DIMSE_receiveCommand(m_assoc, DIMSE_NONBLOCKING, timeout, presID,
-                                message, statusDetail, commandSet);
-  } else {
-    /* call the corresponding DIMSE function to receive the command (use default timeout) */
-    cond = DIMSE_receiveCommand(m_assoc, m_cfg->getDIMSEBlockingMode(), m_cfg->getDIMSETimeout(), presID,
-                                message, statusDetail, commandSet);
-  }
-  return cond;
+    if (m_assoc == NULL)
+        return DIMSE_ILLEGALASSOCIATION;
+
+    OFCondition cond;
+    if (timeout > 0)
+    {
+        /* call the corresponding DIMSE function to receive the command (use specified timeout) */
+        cond = DIMSE_receiveCommand(m_assoc, DIMSE_NONBLOCKING, timeout, presID, message, statusDetail, commandSet);
+    }
+    else
+    {
+        /* call the corresponding DIMSE function to receive the command (use default timeout) */
+        cond = DIMSE_receiveCommand(m_assoc,
+                                    m_cfg->getDIMSEBlockingMode(),
+                                    m_cfg->getDIMSETimeout(),
+                                    presID,
+                                    message,
+                                    statusDetail,
+                                    commandSet);
+    }
+    return cond;
 }
 
 // ----------------------------------------------------------------------------
 
 // Receives one dataset (of instance data) via network from another DICOM application in memory
-OFCondition DcmSCP::receiveDIMSEDataset(T_ASC_PresentationContextID *presID,
-                                        DcmDataset **dataObject)
-{
-  if (m_assoc == NULL)
-    return DIMSE_ILLEGALASSOCIATION;
-
-  OFCondition cond;
-  /* call the corresponding DIMSE function to receive the dataset */
-  if (m_cfg->getProgressNotificationMode())
-  {
-    cond = DIMSE_receiveDataSetInMemory(m_assoc, m_cfg->getDIMSEBlockingMode(), m_cfg->getDIMSETimeout(),
-                                        presID, dataObject, callbackRECEIVEProgress, this /*callbackData*/);
-  } else {
-    cond = DIMSE_receiveDataSetInMemory(m_assoc, m_cfg->getDIMSEBlockingMode(), m_cfg->getDIMSETimeout(),
-                                        presID, dataObject, NULL /*callback*/, NULL /*callbackData*/);
-  }
-
-  if (cond.good())
-  {
-    DCMNET_DEBUG("Received dataset on presentation context " << OFstatic_cast(unsigned int, *presID));
-  } else {
-    OFString tempStr;
-    DCMNET_ERROR("Unable to receive dataset on presentation context "
-      << OFstatic_cast(unsigned int, *presID) << ": " << DimseCondition::dump(tempStr, cond));
-  }
-  return cond;
+OFCondition DcmSCP::receiveDIMSEDataset(T_ASC_PresentationContextID* presID, DcmDataset** dataObject)
+{
+    if (m_assoc == NULL)
+        return DIMSE_ILLEGALASSOCIATION;
+
+    OFCondition cond;
+    /* call the corresponding DIMSE function to receive the dataset */
+    if (m_cfg->getProgressNotificationMode())
+    {
+        cond = DIMSE_receiveDataSetInMemory(m_assoc,
+                                            m_cfg->getDIMSEBlockingMode(),
+                                            m_cfg->getDIMSETimeout(),
+                                            presID,
+                                            dataObject,
+                                            callbackRECEIVEProgress,
+                                            this /*callbackData*/);
+    }
+    else
+    {
+        cond = DIMSE_receiveDataSetInMemory(m_assoc,
+                                            m_cfg->getDIMSEBlockingMode(),
+                                            m_cfg->getDIMSETimeout(),
+                                            presID,
+                                            dataObject,
+                                            NULL /*callback*/,
+                                            NULL /*callbackData*/);
+    }
+
+    if (cond.good())
+    {
+        DCMNET_DEBUG("Received dataset on presentation context " << OFstatic_cast(unsigned int, *presID));
+    }
+    else
+    {
+        OFString tempStr;
+        DCMNET_ERROR("Unable to receive dataset on presentation context "
+                     << OFstatic_cast(unsigned int, *presID) << ": " << DimseCondition::dump(tempStr, cond));
+    }
+    return cond;
 }
 
 // ----------------------------------------------------------------------------
 
 // Receives one C-STORE request dataset via network from another DICOM application
 // (and store it directly to file)
-OFCondition DcmSCP::receiveSTORERequestDataset(T_ASC_PresentationContextID *presID,
-                                               T_DIMSE_C_StoreRQ &reqMessage,
-                                               const OFString &filename)
-{
-  if (m_assoc == NULL)
-    return DIMSE_ILLEGALASSOCIATION;
-  if (filename.empty())
-    return EC_InvalidFilename;
-
-  OFString tempStr;
-  DcmOutputFileStream *filestream = NULL;
-  // Receive dataset over the network and write it directly to a file
-  OFCondition cond = DIMSE_createFilestream(filename, &reqMessage, m_assoc, *presID,
-                                            OFTrue /*writeMetaheader*/, &filestream);
-  if (cond.good())
-  {
-    if (m_cfg->getProgressNotificationMode())
-    {
-      cond = DIMSE_receiveDataSetInFile(m_assoc, m_cfg->getDIMSEBlockingMode(), m_cfg->getDIMSETimeout(),
-                                        presID, filestream, callbackRECEIVEProgress, this /*callbackData*/);
-    } else {
-      cond = DIMSE_receiveDataSetInFile(m_assoc, m_cfg->getDIMSEBlockingMode(), m_cfg->getDIMSETimeout(),
-                                        presID, filestream, NULL /*callback*/, NULL /*callbackData*/);
-    }
-    delete filestream;
+OFCondition DcmSCP::receiveSTORERequestDataset(T_ASC_PresentationContextID* presID,
+                                               T_DIMSE_C_StoreRQ& reqMessage,
+                                               const OFString& filename)
+{
+    if (m_assoc == NULL)
+        return DIMSE_ILLEGALASSOCIATION;
+    if (filename.empty())
+        return EC_InvalidFilename;
+
+    OFString tempStr;
+    DcmOutputFileStream* filestream = NULL;
+    // Receive dataset over the network and write it directly to a file
+    OFCondition cond
+        = DIMSE_createFilestream(filename, &reqMessage, m_assoc, *presID, OFTrue /*writeMetaheader*/, &filestream);
     if (cond.good())
     {
-      DCMNET_DEBUG("Received dataset on presentation context " << OFstatic_cast(unsigned int, *presID)
-        << " and stored it directly to file");
-    } else {
-      DCMNET_ERROR("Unable to receive dataset on presentation context "
-        << OFstatic_cast(unsigned int, *presID) << ": " << DimseCondition::dump(tempStr, cond));
-      // Delete created file in case of error
-      OFStandard::deleteFile(filename);
-    }
-
-  } else {
-
-    DCMNET_ERROR("Unable to receive dataset on presentation context "
-      << OFstatic_cast(unsigned int, *presID) << ": " << DimseCondition::dump(tempStr, cond));
-    // Could not create the filestream, so ignore the dataset
-    DIC_UL bytesRead = 0;
-    DIC_UL pdvCount = 0;
-    DCMNET_DEBUG("Ignoring incoming dataset and returning an error status to the SCU");
-    cond = DIMSE_ignoreDataSet(m_assoc, m_cfg->getDIMSEBlockingMode(), m_cfg->getDIMSETimeout(),
-                               &bytesRead, &pdvCount);
-    if (cond.good())
+        if (m_cfg->getProgressNotificationMode())
+        {
+            cond = DIMSE_receiveDataSetInFile(m_assoc,
+                                              m_cfg->getDIMSEBlockingMode(),
+                                              m_cfg->getDIMSETimeout(),
+                                              presID,
+                                              filestream,
+                                              callbackRECEIVEProgress,
+                                              this /*callbackData*/);
+        }
+        else
+        {
+            cond = DIMSE_receiveDataSetInFile(m_assoc,
+                                              m_cfg->getDIMSEBlockingMode(),
+                                              m_cfg->getDIMSETimeout(),
+                                              presID,
+                                              filestream,
+                                              NULL /*callback*/,
+                                              NULL /*callbackData*/);
+        }
+        delete filestream;
+        if (cond.good())
+        {
+            DCMNET_DEBUG("Received dataset on presentation context " << OFstatic_cast(unsigned int, *presID)
+                                                                     << " and stored it directly to file");
+        }
+        else
+        {
+            DCMNET_ERROR("Unable to receive dataset on presentation context "
+                         << OFstatic_cast(unsigned int, *presID) << ": " << DimseCondition::dump(tempStr, cond));
+            // Delete created file in case of error
+            OFStandard::deleteFile(filename);
+        }
+    }
+    else
     {
-      tempStr = "Cannot create file: " + filename;
-      cond = makeDcmnetCondition(DIMSEC_OUTOFRESOURCES, OF_error, tempStr.c_str());
+
+        DCMNET_ERROR("Unable to receive dataset on presentation context "
+                     << OFstatic_cast(unsigned int, *presID) << ": " << DimseCondition::dump(tempStr, cond));
+        // Could not create the filestream, so ignore the dataset
+        DIC_UL bytesRead = 0;
+        DIC_UL pdvCount  = 0;
+        DCMNET_DEBUG("Ignoring incoming dataset and returning an error status to the SCU");
+        cond = DIMSE_ignoreDataSet(
+            m_assoc, m_cfg->getDIMSEBlockingMode(), m_cfg->getDIMSETimeout(), &bytesRead, &pdvCount);
+        if (cond.good())
+        {
+            tempStr = "Cannot create file: " + filename;
+            cond    = makeDcmnetCondition(DIMSEC_OUTOFRESOURCES, OF_error, tempStr.c_str());
+        }
     }
-  }
-  return cond;
+    return cond;
 }
 
 // ----------------------------------------------------------------------------
 
-OFBool DcmSCP::addStatusDetail(DcmDataset **statusDetail,
-                               const DcmElement *elem)
+OFBool DcmSCP::addStatusDetail(DcmDataset** statusDetail, const DcmElement* elem)
 {
-  DCMNET_TRACE("Add element to status detail");
-  // If no element was passed, return to the caller.
-  if( elem == NULL )
-    return OFFalse;
+    DCMNET_TRACE("Add element to status detail");
+    // If no element was passed, return to the caller.
+    if (elem == NULL)
+        return OFFalse;
 
-  DcmAttributeTag *at;
-  DcmLongString *lo;
+    DcmAttributeTag* at;
+    DcmLongString* lo;
 
-  // Create the container object if necessary
-  if( *statusDetail == NULL )
-    *statusDetail = new DcmDataset();
+    // Create the container object if necessary
+    if (*statusDetail == NULL)
+        *statusDetail = new DcmDataset();
 
-  if (statusDetail == NULL)
-  {
-    DCMNET_ERROR("Cannot create status detail object, memory exhausted!");
-    return OFFalse;
-  }
-
-  // Determine the element's data type
-  DcmVR vr( elem->ident() );
-
-  // Depending on the element's identification, insert different
-  // types of objects into the container.
-  switch( elem->ident() )
-  {
-    case EVR_LO:
-      lo = new DcmLongString( *((DcmLongString*)elem) );
-      if( lo->getLength() > vr.getMaxValueLength() )
-      {
-        DCMNET_WARN("Value inside given LO attribute too large for status detail (max " << OFstatic_cast(Uint32, vr.getMaxValueLength()) << ") for " << vr.getVRName());
-      }
-      (*statusDetail)->insert( lo, OFTrue /*replaceOld*/ );
-      // Print debug information
-      {
-        OFOStringStream oss;
-        lo->print(oss);
-        OFSTRINGSTREAM_GETSTR(oss, strtemp);
-        DCMNET_DEBUG("Adding LO status detail information: " << strtemp);
-        OFSTRINGSTREAM_FREESTR(tmpString)
-      }
-      break;
-    case EVR_AT:
-      at = new DcmAttributeTag( *((DcmAttributeTag*)elem) );
-      if( at->getLength() > vr.getMaxValueLength() )
-      {
-        DCMNET_WARN("Value inside given AT attribute too large for status detail (max " << OFstatic_cast(Uint32, vr.getMaxValueLength()) << ") for " << vr.getVRName());
-      }
-      (*statusDetail)->insert( at, OFTrue /*replaceOld*/ );
-      // Print debug information
-      {
-        OFOStringStream oss;
-        at->print(oss);
-        OFSTRINGSTREAM_GETSTR(oss, strtemp);
-        DCMNET_DEBUG("Adding AT status detail information: " << strtemp);
-        OFSTRINGSTREAM_FREESTR(tmpString)
-      }
-      break;
-    default:  // other status detail is not supported
-      DCMNET_ERROR("Cannot add status detail, unsupported detail attribute type: " << vr.getVRName());
-      return OFFalse;
-      break;
-  }
-  return OFTrue;
+    if (statusDetail == NULL)
+    {
+        DCMNET_ERROR("Cannot create status detail object, memory exhausted!");
+        return OFFalse;
+    }
+
+    // Determine the element's data type
+    DcmVR vr(elem->ident());
+
+    // Depending on the element's identification, insert different
+    // types of objects into the container.
+    switch (elem->ident())
+    {
+        case EVR_LO:
+            lo = new DcmLongString(*((DcmLongString*)elem));
+            if (lo->getLength() > vr.getMaxValueLength())
+            {
+                DCMNET_WARN("Value inside given LO attribute too large for status detail (max "
+                            << OFstatic_cast(Uint32, vr.getMaxValueLength()) << ") for " << vr.getVRName());
+            }
+            (*statusDetail)->insert(lo, OFTrue /*replaceOld*/);
+            // Print debug information
+            {
+                OFOStringStream oss;
+                lo->print(oss);
+                OFSTRINGSTREAM_GETSTR(oss, strtemp);
+                DCMNET_DEBUG("Adding LO status detail information: " << strtemp);
+                OFSTRINGSTREAM_FREESTR(tmpString)
+            }
+            break;
+        case EVR_AT:
+            at = new DcmAttributeTag(*((DcmAttributeTag*)elem));
+            if (at->getLength() > vr.getMaxValueLength())
+            {
+                DCMNET_WARN("Value inside given AT attribute too large for status detail (max "
+                            << OFstatic_cast(Uint32, vr.getMaxValueLength()) << ") for " << vr.getVRName());
+            }
+            (*statusDetail)->insert(at, OFTrue /*replaceOld*/);
+            // Print debug information
+            {
+                OFOStringStream oss;
+                at->print(oss);
+                OFSTRINGSTREAM_GETSTR(oss, strtemp);
+                DCMNET_DEBUG("Adding AT status detail information: " << strtemp);
+                OFSTRINGSTREAM_FREESTR(tmpString)
+            }
+            break;
+        default: // other status detail is not supported
+            DCMNET_ERROR("Cannot add status detail, unsupported detail attribute type: " << vr.getVRName());
+            return OFFalse;
+            break;
+    }
+    return OFTrue;
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::forceAssociationRefuse(const OFBool doRefuse)
 {
-  m_cfg->forceAssociationRefuse(doRefuse);
+    m_cfg->forceAssociationRefuse(doRefuse);
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::setMaxReceivePDULength(const Uint32 maxRecPDU)
 {
-  m_cfg->setMaxReceivePDULength(maxRecPDU);
+    m_cfg->setMaxReceivePDULength(maxRecPDU);
 }
 
 // ----------------------------------------------------------------------------
 
-OFCondition DcmSCP::setEnableVerification(const OFString &profile)
+OFCondition DcmSCP::setEnableVerification(const OFStringprofile)
 {
 
-  OFList<OFString> xfers;
-  xfers.push_back(UID_LittleEndianExplicitTransferSyntax);
-  xfers.push_back(UID_BigEndianExplicitTransferSyntax);
-  xfers.push_back(UID_LittleEndianImplicitTransferSyntax);
-  return m_cfg->addPresentationContext(UID_VerificationSOPClass, xfers, ASC_SC_ROLE_DEFAULT, profile);
+    OFList<OFString> xfers;
+    xfers.push_back(UID_LittleEndianExplicitTransferSyntax);
+    xfers.push_back(UID_BigEndianExplicitTransferSyntax);
+    xfers.push_back(UID_LittleEndianImplicitTransferSyntax);
+    return m_cfg->addPresentationContext(UID_VerificationSOPClass, xfers, ASC_SC_ROLE_DEFAULT, profile);
 }
 
 // ----------------------------------------------------------------------------
 
-
 // ----------------------------------------------------------------------------
 
-OFCondition DcmSCP::addPresentationContext(const OFString &abstractSyntax,
-                                           const OFList<OFString> &xferSyntaxes,
+OFCondition DcmSCP::addPresentationContext(const OFStringabstractSyntax,
+                                           const OFList<OFString>xferSyntaxes,
                                            const T_ASC_SC_ROLE requestorRole,
-                                           const OFString &profile)
+                                           const OFStringprofile)
 {
-  return m_cfg->addPresentationContext(abstractSyntax, xferSyntaxes, requestorRole, profile);
+    return m_cfg->addPresentationContext(abstractSyntax, xferSyntaxes, requestorRole, profile);
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::setPort(const Uint16 port)
 {
-  m_cfg->setPort(port);
+    m_cfg->setPort(port);
 }
 
 // ----------------------------------------------------------------------------
 
-void DcmSCP::setAETitle(const OFString &aetitle)
+void DcmSCP::setAETitle(const OFStringaetitle)
 {
-  m_cfg->setAETitle(aetitle);
+    m_cfg->setAETitle(aetitle);
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::setRespondWithCalledAETitle(const OFBool useCalled)
 {
-  m_cfg->setRespondWithCalledAETitle(useCalled);
+    m_cfg->setRespondWithCalledAETitle(useCalled);
 }
 
 // ----------------------------------------------------------------------------
 
-OFCondition DcmSCP::loadAssociationCfgFile(const OFString &assocFile)
+OFCondition DcmSCP::loadAssociationCfgFile(const OFStringassocFile)
 {
-  return m_cfg->loadAssociationCfgFile(assocFile);
+    return m_cfg->loadAssociationCfgFile(assocFile);
 }
 
 // ----------------------------------------------------------------------------
 
-OFCondition DcmSCP::setAndCheckAssociationProfile(const OFString &profileName)
+OFCondition DcmSCP::setAndCheckAssociationProfile(const OFStringprofileName)
 {
-  return m_cfg->setAndCheckAssociationProfile(profileName);
+    return m_cfg->setAndCheckAssociationProfile(profileName);
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::setConnectionBlockingMode(const DUL_BLOCKOPTIONS blockingMode)
 {
-  m_cfg->setConnectionBlockingMode(blockingMode);
+    m_cfg->setConnectionBlockingMode(blockingMode);
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::setDIMSEBlockingMode(const T_DIMSE_BlockingMode blockingMode)
 {
-  m_cfg->setDIMSEBlockingMode(blockingMode);
+    m_cfg->setDIMSEBlockingMode(blockingMode);
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::setDIMSETimeout(const Uint32 dimseTimeout)
 {
-  m_cfg->setDIMSETimeout(dimseTimeout);
+    m_cfg->setDIMSETimeout(dimseTimeout);
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::setACSETimeout(const Uint32 acseTimeout)
 {
-  m_cfg->setACSETimeout(acseTimeout);
+    m_cfg->setACSETimeout(acseTimeout);
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::setConnectionTimeout(const Uint32 timeout)
 {
-  m_cfg->setConnectionTimeout(timeout);
+    m_cfg->setConnectionTimeout(timeout);
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::setVerbosePCMode(const OFBool mode)
 {
-  m_cfg->setVerbosePCMode(mode);
+    m_cfg->setVerbosePCMode(mode);
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::setHostLookupEnabled(const OFBool mode)
 {
-  m_cfg->setHostLookupEnabled(mode);
+    m_cfg->setHostLookupEnabled(mode);
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::setProgressNotificationMode(const OFBool mode)
 {
-  m_cfg->setProgressNotificationMode(mode);
+    m_cfg->setProgressNotificationMode(mode);
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::setAlwaysAcceptDefaultRole(const OFBool enabled)
 {
-  m_cfg->setAlwaysAcceptDefaultRole(enabled);
+    m_cfg->setAlwaysAcceptDefaultRole(enabled);
 }
 
 // ----------------------------------------------------------------------------
@@ -1780,134 +1904,134 @@ void DcmSCP::setAlwaysAcceptDefaultRole(const OFBool enabled)
 
 OFBool DcmSCP::getRefuseAssociation() const
 {
-  return m_cfg->getRefuseAssociation();
+    return m_cfg->getRefuseAssociation();
 }
 
 // ----------------------------------------------------------------------------
 
 Uint32 DcmSCP::getMaxReceivePDULength() const
 {
-  return m_cfg->getMaxReceivePDULength();
+    return m_cfg->getMaxReceivePDULength();
 }
 
 // ----------------------------------------------------------------------------
 
 Uint16 DcmSCP::getPort() const
 {
-  return m_cfg->getPort();
+    return m_cfg->getPort();
 }
 
 // ----------------------------------------------------------------------------
 
-const OFString &DcmSCP::getAETitle() const
+const OFStringDcmSCP::getAETitle() const
 {
-  return m_cfg->getAETitle();
+    return m_cfg->getAETitle();
 }
 
 // ----------------------------------------------------------------------------
 
 OFBool DcmSCP::getRespondWithCalledAETitle() const
 {
-  return m_cfg->getRespondWithCalledAETitle();
+    return m_cfg->getRespondWithCalledAETitle();
 }
 
 // ----------------------------------------------------------------------------
 
 DUL_BLOCKOPTIONS DcmSCP::getConnectionBlockingMode() const
 {
-  return m_cfg->getConnectionBlockingMode();
+    return m_cfg->getConnectionBlockingMode();
 }
 
 // ----------------------------------------------------------------------------
 
 T_DIMSE_BlockingMode DcmSCP::getDIMSEBlockingMode() const
 {
-  return m_cfg->getDIMSEBlockingMode();
+    return m_cfg->getDIMSEBlockingMode();
 }
 
 // ----------------------------------------------------------------------------
 
 Uint32 DcmSCP::getDIMSETimeout() const
 {
-  return m_cfg->getDIMSETimeout();
+    return m_cfg->getDIMSETimeout();
 }
 
 // ----------------------------------------------------------------------------
 
 Uint32 DcmSCP::getConnectionTimeout() const
 {
-  return m_cfg->getConnectionTimeout();
+    return m_cfg->getConnectionTimeout();
 }
 
 // ----------------------------------------------------------------------------
 
 Uint32 DcmSCP::getACSETimeout() const
 {
-  return m_cfg->getACSETimeout();
+    return m_cfg->getACSETimeout();
 }
 
 // ----------------------------------------------------------------------------
 
 OFBool DcmSCP::getVerbosePCMode() const
 {
-  return m_cfg->getVerbosePCMode();
+    return m_cfg->getVerbosePCMode();
 }
 
 // ----------------------------------------------------------------------------
 
 OFBool DcmSCP::getHostLookupEnabled() const
 {
-  return m_cfg->getHostLookupEnabled();
+    return m_cfg->getHostLookupEnabled();
 }
 
 // ----------------------------------------------------------------------------
 
 OFBool DcmSCP::getProgressNotificationMode() const
 {
-  return m_cfg->getProgressNotificationMode();
+    return m_cfg->getProgressNotificationMode();
 }
 
 // ----------------------------------------------------------------------------
 
 OFBool DcmSCP::isConnected() const
 {
-  return (m_assoc != NULL) && (m_assoc->DULassociation != NULL);
+    return (m_assoc != NULL) && (m_assoc->DULassociation != NULL);
 }
 
 // ----------------------------------------------------------------------------
 
 OFString DcmSCP::getPeerAETitle() const
 {
-  if (m_assoc == NULL)
-    return "";
-  return m_assoc->params->DULparams.callingAPTitle;
+    if (m_assoc == NULL)
+        return "";
+    return m_assoc->params->DULparams.callingAPTitle;
 }
 
 // ----------------------------------------------------------------------------
 
 OFString DcmSCP::getCalledAETitle() const
 {
-  if (m_assoc == NULL)
-    return "";
-  return m_assoc->params->DULparams.calledAPTitle;
+    if (m_assoc == NULL)
+        return "";
+    return m_assoc->params->DULparams.calledAPTitle;
 }
 
 // ----------------------------------------------------------------------------
 
 Uint32 DcmSCP::getPeerMaxPDULength() const
 {
-  if (m_assoc == NULL)
-    return 0;
-  return m_assoc->params->theirMaxPDUReceiveSize;
+    if (m_assoc == NULL)
+        return 0;
+    return m_assoc->params->theirMaxPDUReceiveSize;
 }
 
 // ----------------------------------------------------------------------------
 
 OFString DcmSCP::getPeerIP() const
 {
-  if (m_assoc == NULL)
-    return "";
-  return m_assoc->params->DULparams.callingPresentationAddress;
+    if (m_assoc == NULL)
+        return "";
+    return m_assoc->params->DULparams.callingPresentationAddress;
 }
 
 // ----------------------------------------------------------------------------
@@ -1915,155 +2039,148 @@ OFString DcmSCP::getPeerIP() const
 void DcmSCP::dropAndDestroyAssociation()
 {
 
-  if (m_assoc)
-  {
-    ASC_dropSCPAssociation( m_assoc );
-    ASC_destroyAssociation( &m_assoc );
-  }
+    if (m_assoc)
+    {
+        ASC_dropSCPAssociation(m_assoc);
+        ASC_destroyAssociation(&m_assoc);
+    }
 }
 
-
 /* ************************************************************************** */
 /*                            Notify functions                                */
 /* ************************************************************************** */
 
-
-void DcmSCP::notifyAssociationRequest(const T_ASC_Parameters &params,
-                                      DcmSCPActionType & /* desiredAction */)
+void DcmSCP::notifyAssociationRequest(const T_ASC_Parameters& params, DcmSCPActionType& /* desiredAction */)
 {
-  // Dump some information if required
-  DCMNET_INFO("Association Received " << params.DULparams.callingPresentationAddress << ": "
-                                      << params.DULparams.callingAPTitle << " -> "
-                                      << params.DULparams.calledAPTitle);
+    // Dump some information if required
+    DCMNET_INFO("Association Received " << params.DULparams.callingPresentationAddress << ": "
+                                        << params.DULparams.callingAPTitle << " -> " << params.DULparams.calledAPTitle);
 
     // Dump more information if required
-  OFString tempStr;
-  if (m_cfg->getVerbosePCMode())
-    DCMNET_INFO("Incoming Association Request:" << OFendl << ASC_dumpParameters(tempStr, m_assoc->params, ASC_ASSOC_RQ));
-  else
-    DCMNET_DEBUG("Incoming Association Request:" << OFendl << ASC_dumpParameters(tempStr, m_assoc->params, ASC_ASSOC_RQ));
+    OFString tempStr;
+    if (m_cfg->getVerbosePCMode())
+        DCMNET_INFO("Incoming Association Request:" << OFendl
+                                                    << ASC_dumpParameters(tempStr, m_assoc->params, ASC_ASSOC_RQ));
+    else
+        DCMNET_DEBUG("Incoming Association Request:" << OFendl
+                                                     << ASC_dumpParameters(tempStr, m_assoc->params, ASC_ASSOC_RQ));
 }
 
 // ----------------------------------------------------------------------------
 
 OFBool DcmSCP::checkCalledAETitleAccepted(const OFString& /*calledAETitle*/)
 {
-  return OFTrue;
+    return OFTrue;
 }
 
 // ----------------------------------------------------------------------------
 
 OFBool DcmSCP::checkCallingAETitleAccepted(const OFString& /*callingAETitle*/)
 {
-  return OFTrue;
+    return OFTrue;
 }
 
 // ----------------------------------------------------------------------------
 
 OFBool DcmSCP::checkCallingHostAccepted(const OFString& /*hostOrIP*/)
 {
-  return OFTrue;
+    return OFTrue;
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::notifyAssociationAcknowledge()
 {
-  DCMNET_DEBUG("DcmSCP: Association Acknowledged");
+    DCMNET_DEBUG("DcmSCP: Association Acknowledged");
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::notifyReleaseRequest()
 {
-  DCMNET_INFO("Received Association Release Request");
+    DCMNET_INFO("Received Association Release Request");
 }
 
-
 // ----------------------------------------------------------------------------
 
 void DcmSCP::notifyAbortRequest()
 {
-  DCMNET_INFO("Received Association Abort Request");
+    DCMNET_INFO("Received Association Abort Request");
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::notifyAssociationTermination()
 {
-  DCMNET_DEBUG("DcmSCP: Association Terminated");
+    DCMNET_DEBUG("DcmSCP: Association Terminated");
 }
 
 // ----------------------------------------------------------------------------
 
 void DcmSCP::notifyConnectionTimeout()
 {
-  DCMNET_TRACE("Connection timeout encountered in non-blocking mode");
+    DCMNET_TRACE("Connection timeout encountered in non-blocking mode");
 }
 
 // ----------------------------------------------------------------------------
 
-void DcmSCP::notifyDIMSEError(const OFCondition &cond)
+void DcmSCP::notifyDIMSEError(const OFConditioncond)
 {
-  OFString tempStr;
-  DCMNET_DEBUG("DIMSE Error, detail (if available): " << DimseCondition::dump(tempStr, cond));
+    OFString tempStr;
+    DCMNET_DEBUG("DIMSE Error, detail (if available): " << DimseCondition::dump(tempStr, cond));
 }
 
 // ----------------------------------------------------------------------------
 
 OFBool DcmSCP::stopAfterCurrentAssociation()
 {
-  return OFFalse;
+    return OFFalse;
 }
 
 // ----------------------------------------------------------------------------
 
 OFBool DcmSCP::stopAfterConnectionTimeout()
 {
-  return OFFalse;
+    return OFFalse;
 }
 
-
 /* ************************************************************************* */
 /*                            Callback functions                             */
 /* ************************************************************************* */
 
-void DcmSCP::callbackSENDProgress(void *callbackContext,
-                                  const unsigned long byteCount)
+void DcmSCP::callbackSENDProgress(void* callbackContext, const unsigned long byteCount)
 {
-  if (callbackContext != NULL)
-    OFreinterpret_cast(DcmSCP *, callbackContext)->notifySENDProgress(byteCount);
+    if (callbackContext != NULL)
+        OFreinterpret_cast(DcmSCP*, callbackContext)->notifySENDProgress(byteCount);
 }
 
-
-void DcmSCP::callbackRECEIVEProgress(void *callbackContext,
-                                     const unsigned long byteCount)
+void DcmSCP::callbackRECEIVEProgress(void* callbackContext, const unsigned long byteCount)
 {
-  if (callbackContext != NULL)
-    OFreinterpret_cast(DcmSCP *, callbackContext)->notifyRECEIVEProgress(byteCount);
+    if (callbackContext != NULL)
+        OFreinterpret_cast(DcmSCP*, callbackContext)->notifyRECEIVEProgress(byteCount);
 }
 
-
 /* ************************************************************************* */
 /*                         Static helper functions                           */
 /* ************************************************************************* */
 
-OFBool DcmSCP::getPresentationContextInfo(const T_ASC_Association *assoc,
+OFBool DcmSCP::getPresentationContextInfo(const T_ASC_Associationassoc,
                                           const Uint8 presID,
-                                          DcmPresentationContextInfo &presInfo)
-{
-  if (assoc != NULL)
-  {
-    DUL_PRESENTATIONCONTEXT *pc = findPresentationContextID(assoc->params->DULparams.acceptedPresentationContext, presID);
-    if (pc != NULL)
-    {
-      presInfo.abstractSyntax = pc->abstractSyntax;
-      presInfo.acceptedTransferSyntax = pc->acceptedTransferSyntax;
-      presInfo.presentationContextID = pc->presentationContextID;
-      presInfo.proposedSCRole = pc->proposedSCRole;
-      presInfo.acceptedSCRole = pc->acceptedSCRole;
-      return OFTrue;
-    }
-  }
-  return OFFalse;
+                                          DcmPresentationContextInfo& presInfo)
+{
+    if (assoc != NULL)
+    {
+        DUL_PRESENTATIONCONTEXT* pc
+            = findPresentationContextID(assoc->params->DULparams.acceptedPresentationContext, presID);
+        if (pc != NULL)
+        {
+            presInfo.abstractSyntax         = pc->abstractSyntax;
+            presInfo.acceptedTransferSyntax = pc->acceptedTransferSyntax;
+            presInfo.presentationContextID  = pc->presentationContextID;
+            presInfo.proposedSCRole         = pc->proposedSCRole;
+            presInfo.acceptedSCRole         = pc->acceptedSCRole;
+            return OFTrue;
+        }
+    }
+    return OFFalse;
 }
index 61e7f7bd5c4cebb5316f1d0dfbdd31b6194cb3f9..5debde1f1c5bdd697074d9ad9eb049bd46a5d79c 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2012-2017, OFFIS e.V.
+ *  Copyright (C) 2012-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -20,7 +20,6 @@
  */
 
 #include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
-
 #include "dcmtk/dcmnet/scpcfg.h"
 #include "dcmtk/dcmnet/diutil.h"
 
@@ -40,7 +39,8 @@ DcmSCPConfig::DcmSCPConfig() :
   m_verbosePCMode(OFFalse),
   m_connectionTimeout(1000),
   m_respondWithCalledAETitle(OFTrue),
-  m_progressNotificationMode(OFTrue)
+  m_progressNotificationMode(OFTrue),
+  m_tLayer(NULL)
 {
 }
 
@@ -297,6 +297,27 @@ OFBool DcmSCPConfig::getProgressNotificationMode() const
 
 // ----------------------------------------------------------------------------
 
+OFBool DcmSCPConfig::transportLayerEnabled() const
+{
+  return (m_tLayer != NULL);
+}
+
+// ----------------------------------------------------------------------------
+
+DcmTransportLayer * DcmSCPConfig::getTransportLayer() const
+{
+    return m_tLayer;
+}
+
+// ----------------------------------------------------------------------------
+
+void DcmSCPConfig::setTransportLayer(DcmTransportLayer *tlayer)
+{
+  m_tLayer = tlayer;
+}
+
+// ----------------------------------------------------------------------------
+
 // Reads association configuration from config file
 OFCondition DcmSCPConfig::loadAssociationCfgFile(const OFString &assocFile)
 {
index a20b07c1fbd04556459360025066ba4f5ffb298a..50a2951de6fb18d290a13bac702f338555029b9e 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2012-2014, OFFIS e.V.
+ *  Copyright (C) 2012-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -28,6 +28,7 @@
 
 #include "dcmtk/dcmnet/scppool.h"
 #include "dcmtk/dcmnet/diutil.h"
+#include "dcmtk/dcmtls/tlslayer.h"
 
 // ----------------------------------------------------------------------------
 
@@ -64,6 +65,15 @@ OFCondition DcmBaseSCPPool::listen()
   if( cond.bad() )
     return cond;
 
+  if (m_cfg.transportLayerEnabled())
+  {
+    cond = ASC_setTransportLayer(network, m_cfg.getTransportLayer(), 0 /* Do not take over ownership */);
+    if (cond.bad())
+    {
+        DCMNET_ERROR("DcmBaseSCPPool: Error setting secured transport layer: " << cond.text());
+    }
+  }
+
   /* As long as all is fine (or we have been to busy handling last connection request) keep listening */
   while ( m_runMode == LISTEN && ( cond.good() || (cond == NET_EC_SCPBusy) ) )
   {
@@ -71,8 +81,10 @@ OFCondition DcmBaseSCPPool::listen()
     cond = EC_Normal;
     // Every incoming connection is handled in a new association object
     T_ASC_Association *assoc = NULL;
+    OFBool useSecureLayer = m_cfg.transportLayerEnabled();
+
     // Listen to a socket for timeout seconds for an association request, accepts TCP connection.
-    cond = ASC_receiveAssociation( network, &assoc, m_cfg.getMaxReceivePDULength(), NULL, NULL, OFFalse,
+    cond = ASC_receiveAssociation( network, &assoc, m_cfg.getMaxReceivePDULength(), NULL, NULL, useSecureLayer,
         m_cfg.getConnectionBlockingMode(), OFstatic_cast(int, m_cfg.getConnectionTimeout()) );
 
     /* If we have a connection request, try to find/create a worker to handle it */
index 153ea3c202d7d0f2ae9262b4c8aa230025c9e15f..1e4dd631d8d36f96407db5e259f817b401da684e 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2008-2018, OFFIS e.V.
+ *  Copyright (C) 2008-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
  *
  */
 
-#include "dcmtk/config/osconfig.h"  /* make sure OS specific configuration is included first */
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 
-#include "dcmtk/dcmnet/scu.h"
-#include "dcmtk/dcmnet/diutil.h"    /* for dcmnet logger */
-#include "dcmtk/dcmdata/dcuid.h"    /* for dcmFindUIDName() */
 #include "dcmtk/dcmdata/dcostrmf.h" /* for class DcmOutputFileStream */
-#include "dcmtk/ofstd/ofmem.h"      /* for OFunique_ptr */
+#include "dcmtk/dcmdata/dcuid.h"    /* for dcmFindUIDName() */
+#include "dcmtk/dcmnet/diutil.h"    /* for dcmnet logger */
+#include "dcmtk/dcmnet/scu.h"
+#include "dcmtk/ofstd/ofmem.h" /* for OFunique_ptr */
 
 #ifdef WITH_ZLIB
-#include <zlib.h>                   /* for zlibVersion() */
+#include <zlib.h> /* for zlibVersion() */
 #endif
 
-
-DcmSCU::DcmSCU() :
-  m_assoc(NULL),
-  m_net(NULL),
-  m_params(NULL),
-  m_assocConfigFilename(),
-  m_assocConfigProfile(),
-  m_presContexts(),
-  m_assocConfigFile(),
-  m_openDIMSERequest(NULL),
-  m_maxReceivePDULength(ASC_DEFAULTMAXPDU),
-  m_blockMode(DIMSE_BLOCKING),
-  m_ourAETitle("ANY-SCU"),
-  m_peer(),
-  m_peerAETitle("ANY-SCP"),
-  m_peerPort(104),
-  m_dimseTimeout(0),
-  m_acseTimeout(30),
-  m_storageDir(),
-  m_storageMode(DCMSCU_STORAGE_DISK),
-  m_verbosePCMode(OFFalse),
-  m_datasetConversionMode(OFFalse),
-  m_progressNotificationMode(OFTrue)
-{
-  OFStandard::initializeNetwork();
+DcmSCU::DcmSCU()
+    : m_assoc(NULL)
+    , m_net(NULL)
+    , m_params(NULL)
+    , m_assocConfigFilename()
+    , m_assocConfigProfile()
+    , m_presContexts()
+    , m_assocConfigFile()
+    , m_openDIMSERequest(NULL)
+    , m_maxReceivePDULength(ASC_DEFAULTMAXPDU)
+    , m_blockMode(DIMSE_BLOCKING)
+    , m_ourAETitle("ANY-SCU")
+    , m_peer()
+    , m_peerAETitle("ANY-SCP")
+    , m_peerPort(104)
+    , m_dimseTimeout(0)
+    , m_acseTimeout(30)
+    , m_storageDir()
+    , m_storageMode(DCMSCU_STORAGE_DISK)
+    , m_verbosePCMode(OFFalse)
+    , m_datasetConversionMode(OFFalse)
+    , m_progressNotificationMode(OFTrue)
+{
+    OFStandard::initializeNetwork();
 }
 
 void DcmSCU::freeNetwork()
 {
-  if ((m_assoc != NULL) || (m_net != NULL) || (m_params != NULL))
-    DCMNET_DEBUG("Cleaning up internal association and network structures");
-  /* destroy association parameters, i.e. free memory of T_ASC_Parameters.
-     Usually this is done in ASC_destroyAssociation; however, if we already
-     have association parameters but not yet an association (e.g. after calling
-     initNetwork() and negotiateAssociation()), the latter approach may fail.
-  */
-  if (m_params)
-  {
-    ASC_destroyAssociationParameters(&m_params);
-    m_params = NULL;
-    // make sure destroyAssociation does not try to free params a second time
-    // (happens in case we have already have an association structure)
-    if (m_assoc)
-      m_assoc->params = NULL;
-  }
-  // destroy the association, i.e. free memory of T_ASC_Association* structure.
-  ASC_destroyAssociation(&m_assoc);
-  // drop the network, i.e. free memory of T_ASC_Network* structure.
-  ASC_dropNetwork(&m_net);
-  // Cleanup old DIMSE request if any
-  delete m_openDIMSERequest;
-  m_openDIMSERequest = NULL;
+    if ((m_assoc != NULL) || (m_net != NULL) || (m_params != NULL))
+        DCMNET_DEBUG("Cleaning up internal association and network structures");
+    /* destroy association parameters, i.e. free memory of T_ASC_Parameters.
+       Usually this is done in ASC_destroyAssociation; however, if we already
+       have association parameters but not yet an association (e.g. after calling
+       initNetwork() and negotiateAssociation()), the latter approach may fail.
+    */
+    if (m_params)
+    {
+        ASC_destroyAssociationParameters(&m_params);
+        m_params = NULL;
+        // make sure destroyAssociation does not try to free params a second time
+        // (happens in case we have already have an association structure)
+        if (m_assoc)
+            m_assoc->params = NULL;
+    }
+    // destroy the association, i.e. free memory of T_ASC_Association* structure.
+    ASC_destroyAssociation(&m_assoc);
+    // drop the network, i.e. free memory of T_ASC_Network* structure.
+    ASC_dropNetwork(&m_net);
+    // Cleanup old DIMSE request if any
+    delete m_openDIMSERequest;
+    m_openDIMSERequest = NULL;
 }
 
-
 DcmSCU::~DcmSCU()
 {
-  // abort association (if any) and destroy dcmnet data structures
-  if (isConnected())
-  {
-    closeAssociation(DCMSCU_ABORT_ASSOCIATION); // also frees network
-  } else {
-    freeNetwork();
-  }
+    // abort association (if any) and destroy dcmnet data structures
+    if (isConnected())
+    {
+        closeAssociation(DCMSCU_ABORT_ASSOCIATION); // also frees network
+    }
+    else
+    {
+        freeNetwork();
+    }
 
-  OFStandard::shutdownNetwork();
+    OFStandard::shutdownNetwork();
 }
 
-
 OFCondition DcmSCU::initNetwork()
 {
-  /* Return if SCU is already connected */
-  if (isConnected())
-    return NET_EC_AlreadyConnected;
+    /* Return if SCU is already connected */
+    if (isConnected())
+        return NET_EC_AlreadyConnected;
 
-  /* Be sure internal network structures are clean (delete old) */
-  freeNetwork();
+    /* Be sure internal network structures are clean (delete old) */
+    freeNetwork();
 
-  OFString tempStr;
-  /* initialize network, i.e. create an instance of T_ASC_Network*. */
-  OFCondition cond = ASC_initializeNetwork(NET_REQUESTOR, 0, m_acseTimeout, &m_net);
-  if (cond.bad())
-  {
-    DimseCondition::dump(tempStr, cond);
-    DCMNET_ERROR(tempStr);
-    return cond;
-  }
+    OFString tempStr;
+    /* initialize network, i.e. create an instance of T_ASC_Network*. */
+    OFCondition cond = ASC_initializeNetwork(NET_REQUESTOR, 0, m_acseTimeout, &m_net);
+    if (cond.bad())
+    {
+        DimseCondition::dump(tempStr, cond);
+        DCMNET_ERROR(tempStr);
+        return cond;
+    }
 
-  /* initialize association parameters, i.e. create an instance of T_ASC_Parameters*. */
-  cond = ASC_createAssociationParameters(&m_params, m_maxReceivePDULength);
-  if (cond.bad())
-  {
-    DCMNET_ERROR(DimseCondition::dump(tempStr, cond));
-    return cond;
-  }
+    /* initialize association parameters, i.e. create an instance of T_ASC_Parameters*. */
+    cond = ASC_createAssociationParameters(&m_params, m_maxReceivePDULength);
+    if (cond.bad())
+    {
+        DCMNET_ERROR(DimseCondition::dump(tempStr, cond));
+        return cond;
+    }
 
-  /* sets this application's title and the called application's title in the params */
-  /* structure. The default values are "ANY-SCU" and "ANY-SCP". */
-  ASC_setAPTitles(m_params, m_ourAETitle.c_str(), m_peerAETitle.c_str(), NULL);
-
-  /* Figure out the presentation addresses and copy the */
-  /* corresponding values into the association parameters.*/
-  DIC_NODENAME peerHost;
-  const OFString localHost = OFStandard::getHostName();
-  /* Since the underlying dcmnet structures reserve only 64 bytes for peer
-     as well as local host name, we check here for buffer overflow.
-   */
-  if ((m_peer.length() + 5 /* max 65535 */) + 1 /* for ":" */ > 63)
-  {
-    DCMNET_ERROR("Maximum length of peer host name '" << m_peer << "' is longer than maximum of 57 characters");
-    return EC_IllegalCall; // TODO: need to find better error code
-  }
-  if (localHost.size() + 1 > 63)
-  {
-    DCMNET_ERROR("Maximum length of local host name '" << localHost << "' is longer than maximum of 62 characters");
-    return EC_IllegalCall; // TODO: need to find better error code
-  }
-  sprintf(peerHost, "%s:%d", m_peer.c_str(), OFstatic_cast(int, m_peerPort));
-  ASC_setPresentationAddresses(m_params, localHost.c_str(), peerHost);
+    /* sets this application's title and the called application's title in the params */
+    /* structure. The default values are "ANY-SCU" and "ANY-SCP". */
+    ASC_setAPTitles(m_params, m_ourAETitle.c_str(), m_peerAETitle.c_str(), NULL);
+
+    /* Figure out the presentation addresses and copy the */
+    /* corresponding values into the association parameters.*/
+    DIC_NODENAME peerHost;
+    const OFString localHost = OFStandard::getHostName();
+    /* Since the underlying dcmnet structures reserve only 64 bytes for peer
+       as well as local host name, we check here for buffer overflow.
+     */
+    if ((m_peer.length() + 5 /* max 65535 */) + 1 /* for ":" */ > 63)
+    {
+        DCMNET_ERROR("Maximum length of peer host name '" << m_peer << "' is longer than maximum of 57 characters");
+        return EC_IllegalCall; // TODO: need to find better error code
+    }
+    if (localHost.size() + 1 > 63)
+    {
+        DCMNET_ERROR("Maximum length of local host name '" << localHost << "' is longer than maximum of 62 characters");
+        return EC_IllegalCall; // TODO: need to find better error code
+    }
+    sprintf(peerHost, "%s:%d", m_peer.c_str(), OFstatic_cast(int, m_peerPort));
+    ASC_setPresentationAddresses(m_params, localHost.c_str(), peerHost);
 
-  /* Add presentation contexts */
+    /* Add presentation contexts */
 
-  // First, import from config file, if specified
-  OFCondition result;
-  if (!m_assocConfigFilename.empty())
-  {
-    DcmAssociationConfiguration assocConfig;
-    result = DcmAssociationConfigurationFile::initialize(assocConfig, m_assocConfigFilename.c_str());
-    if (result.bad())
+    // First, import from config file, if specified
+    OFCondition result;
+    if (!m_assocConfigFilename.empty())
     {
-      DCMNET_WARN("Unable to parse association configuration file " << m_assocConfigFilename
-        << " (ignored): " << result.text());
-      return result;
+        DcmAssociationConfiguration assocConfig;
+        result = DcmAssociationConfigurationFile::initialize(assocConfig, m_assocConfigFilename.c_str());
+        if (result.bad())
+        {
+            DCMNET_WARN("Unable to parse association configuration file " << m_assocConfigFilename
+                                                                          << " (ignored): " << result.text());
+            return result;
+        }
+        else
+        {
+            /* perform name mangling for config file key */
+            OFString profileName;
+            const unsigned char* c = OFreinterpret_cast(const unsigned char*, m_assocConfigProfile.c_str());
+            while (*c)
+            {
+                if (!isspace(*c))
+                    profileName += OFstatic_cast(char, toupper(*c));
+                ++c;
+            }
+
+            result = assocConfig.setAssociationParameters(profileName.c_str(), *m_params);
+            if (result.bad())
+            {
+                DCMNET_WARN("Unable to apply association configuration file " << m_assocConfigFilename
+                                                                              << " (ignored): " << result.text());
+                return result;
+            }
+        }
+    }
+
+    // Adapt presentation context ID to existing presentation contexts.
+    // It's important that presentation context IDs are numerated 1,3,5,7...!
+    Uint32 nextFreePresID = 257;
+    Uint32 numContexts    = ASC_countPresentationContexts(m_params);
+    if (numContexts <= 127)
+    {
+        // Need Uint16 to avoid overflow in currPresID (unsigned char)
+        nextFreePresID = 2 * numContexts + 1; /* add 1 to point to the next free ID*/
+    }
+    // Print warning if number of overall presentation contexts exceeds 128
+    if ((numContexts + m_presContexts.size()) > 128)
+    {
+        DCMNET_WARN("Number of presentation contexts exceeds 128 (" << numContexts + m_presContexts.size()
+                                                                    << "). Some contexts will not be negotiated");
     }
     else
     {
-      /* perform name mangling for config file key */
-      OFString profileName;
-      const unsigned char *c = OFreinterpret_cast(const unsigned char *, m_assocConfigProfile.c_str());
-      while (*c)
-      {
-        if (! isspace(*c)) profileName += OFstatic_cast(char, toupper(*c));
-        ++c;
-      }
-
-      result = assocConfig.setAssociationParameters(profileName.c_str(), *m_params);
-      if (result.bad())
-      {
-        DCMNET_WARN("Unable to apply association configuration file " << m_assocConfigFilename
-          <<" (ignored): " << result.text());
-        return result;
-      }
+        DCMNET_TRACE("Configured " << numContexts << " presentation contexts from config file");
+        if (m_presContexts.size() > 0)
+            DCMNET_TRACE("Adding another " << m_presContexts.size() << " presentation contexts configured for SCU");
     }
-  }
 
-  // Adapt presentation context ID to existing presentation contexts.
-  // It's important that presentation context IDs are numerated 1,3,5,7...!
-  Uint32 nextFreePresID = 257;
-  Uint32 numContexts = ASC_countPresentationContexts(m_params);
-  if (numContexts <= 127)
-  {
-    // Need Uint16 to avoid overflow in currPresID (unsigned char)
-    nextFreePresID = 2 * numContexts + 1; /* add 1 to point to the next free ID*/
-  }
-  // Print warning if number of overall presentation contexts exceeds 128
-  if ((numContexts + m_presContexts.size()) > 128)
-  {
-    DCMNET_WARN("Number of presentation contexts exceeds 128 (" << numContexts + m_presContexts.size()
-      << "). Some contexts will not be negotiated");
-  }
-  else
-  {
-    DCMNET_TRACE("Configured " << numContexts << " presentation contexts from config file");
-    if (m_presContexts.size() > 0)
-      DCMNET_TRACE("Adding another " << m_presContexts.size() << " presentation contexts configured for SCU");
-  }
+    // Add presentation contexts not originating from config file
+    OFListIterator(DcmSCUPresContext) contIt             = m_presContexts.begin();
+    OFListConstIterator(DcmSCUPresContext) endOfContList = m_presContexts.end();
+    while ((contIt != endOfContList) && (nextFreePresID <= 255))
+    {
+        const Uint16 numTransferSyntaxes = OFstatic_cast(Uint16, (*contIt).transferSyntaxes.size());
+        const char** transferSyntaxes    = new const char*[numTransferSyntaxes];
+
+        // Iterate over transfer syntaxes within one presentation context
+        OFListIterator(OFString) syntaxIt        = (*contIt).transferSyntaxes.begin();
+        OFListIterator(OFString) endOfSyntaxList = (*contIt).transferSyntaxes.end();
+        Uint16 sNum                              = 0;
+        // copy all transfer syntaxes to array
+        while (syntaxIt != endOfSyntaxList)
+        {
+            transferSyntaxes[sNum] = (*syntaxIt).c_str();
+            ++syntaxIt;
+            ++sNum;
+        }
 
-  // Add presentation contexts not originating from config file
-  OFListIterator(DcmSCUPresContext) contIt = m_presContexts.begin();
-  OFListConstIterator(DcmSCUPresContext) endOfContList = m_presContexts.end();
-  while ((contIt != endOfContList) && (nextFreePresID <= 255))
-  {
-    const Uint16 numTransferSyntaxes = OFstatic_cast(Uint16, (*contIt).transferSyntaxes.size());
-    const char** transferSyntaxes = new const char*[numTransferSyntaxes];
-
-    // Iterate over transfer syntaxes within one presentation context
-    OFListIterator(OFString) syntaxIt = (*contIt).transferSyntaxes.begin();
-    OFListIterator(OFString) endOfSyntaxList = (*contIt).transferSyntaxes.end();
-    Uint16 sNum = 0;
-    // copy all transfer syntaxes to array
-    while (syntaxIt != endOfSyntaxList)
-    {
-      transferSyntaxes[sNum] = (*syntaxIt).c_str();
-      ++syntaxIt;
-      ++sNum;
-    }
-
-    // add the presentation context
-    cond = ASC_addPresentationContext(m_params, OFstatic_cast(Uint8, nextFreePresID),
-      (*contIt).abstractSyntaxName.c_str(), transferSyntaxes, numTransferSyntaxes,(*contIt).roleSelect);
-    // if adding was successful, prepare presentation context ID for next addition
-    delete[] transferSyntaxes;
-    transferSyntaxes = NULL;
-    if (cond.bad())
-      return cond;
-    contIt++;
-    // goto next free number, only odd presentation context IDs permitted
-    nextFreePresID += 2;
-  }
+        // add the presentation context
+        cond = ASC_addPresentationContext(m_params,
+                                          OFstatic_cast(Uint8, nextFreePresID),
+                                          (*contIt).abstractSyntaxName.c_str(),
+                                          transferSyntaxes,
+                                          numTransferSyntaxes,
+                                          (*contIt).roleSelect);
+        // if adding was successful, prepare presentation context ID for next addition
+        delete[] transferSyntaxes;
+        transferSyntaxes = NULL;
+        if (cond.bad())
+            return cond;
+        contIt++;
+        // goto next free number, only odd presentation context IDs permitted
+        nextFreePresID += 2;
+    }
 
-  numContexts = ASC_countPresentationContexts(m_params);
-  if (numContexts == 0)
-  {
-    DCMNET_ERROR("Cannot initialize network: No presentation contexts defined");
-    return NET_EC_NoPresentationContextsDefined;
-  }
-  DCMNET_DEBUG("Configured a total of " << numContexts << " presentation contexts for SCU");
+    numContexts = ASC_countPresentationContexts(m_params);
+    if (numContexts == 0)
+    {
+        DCMNET_ERROR("Cannot initialize network: No presentation contexts defined");
+        return NET_EC_NoPresentationContextsDefined;
+    }
+    DCMNET_DEBUG("Configured a total of " << numContexts << " presentation contexts for SCU");
 
-  return cond;
+    return cond;
 }
 
-
 OFCondition DcmSCU::negotiateAssociation()
 {
-  /* Return error if SCU is already connected */
-  if (isConnected())
-    return NET_EC_AlreadyConnected;
-
-  /* dump presentation contexts if required */
-  OFString tempStr;
-  if (m_verbosePCMode)
-    DCMNET_INFO("Request Parameters:" << OFendl << ASC_dumpParameters(tempStr, m_params, ASC_ASSOC_RQ));
-  else
-    DCMNET_DEBUG("Request Parameters:" << OFendl << ASC_dumpParameters(tempStr, m_params, ASC_ASSOC_RQ));
-
-  /* create association, i.e. try to establish a network connection to another */
-  /* DICOM application. This call creates an instance of T_ASC_Association*. */
-  DCMNET_INFO("Requesting Association");
-  OFCondition cond = ASC_requestAssociation(m_net, m_params, &m_assoc);
-  if (cond.bad())
-  {
-    if (cond == DUL_ASSOCIATIONREJECTED)
-    {
-      T_ASC_RejectParameters rej;
-      ASC_getRejectParameters(m_params, &rej);
-      DCMNET_DEBUG("Association Rejected:" << OFendl << ASC_printRejectParameters(tempStr, &rej));
-      return cond;
-    }
+    /* Return error if SCU is already connected */
+    if (isConnected())
+        return NET_EC_AlreadyConnected;
+
+    /* dump presentation contexts if required */
+    OFString tempStr;
+    if (m_verbosePCMode)
+        DCMNET_INFO("Request Parameters:" << OFendl << ASC_dumpParameters(tempStr, m_params, ASC_ASSOC_RQ));
     else
+        DCMNET_DEBUG("Request Parameters:" << OFendl << ASC_dumpParameters(tempStr, m_params, ASC_ASSOC_RQ));
+
+    /* create association, i.e. try to establish a network connection to another */
+    /* DICOM application. This call creates an instance of T_ASC_Association*. */
+    DCMNET_INFO("Requesting Association");
+    OFCondition cond = ASC_requestAssociation(m_net, m_params, &m_assoc);
+    if (cond.bad())
     {
-      DCMNET_DEBUG("Association Request Failed: " << DimseCondition::dump(tempStr, cond));
-      return cond;
+        if (cond == DUL_ASSOCIATIONREJECTED)
+        {
+            T_ASC_RejectParameters rej;
+            ASC_getRejectParameters(m_params, &rej);
+            DCMNET_DEBUG("Association Rejected:" << OFendl << ASC_printRejectParameters(tempStr, &rej));
+            return cond;
+        }
+        else
+        {
+            DCMNET_DEBUG("Association Request Failed: " << DimseCondition::dump(tempStr, cond));
+            return cond;
+        }
     }
-  }
 
-  /* dump the presentation contexts which have been accepted/refused */
-  if (m_verbosePCMode)
-    DCMNET_INFO("Association Parameters Negotiated:" << OFendl << ASC_dumpParameters(tempStr, m_params, ASC_ASSOC_AC));
-  else
-    DCMNET_DEBUG("Association Parameters Negotiated:" << OFendl << ASC_dumpParameters(tempStr, m_params, ASC_ASSOC_AC));
+    /* dump the presentation contexts which have been accepted/refused */
+    if (m_verbosePCMode)
+        DCMNET_INFO("Association Parameters Negotiated:" << OFendl
+                                                         << ASC_dumpParameters(tempStr, m_params, ASC_ASSOC_AC));
+    else
+        DCMNET_DEBUG("Association Parameters Negotiated:" << OFendl
+                                                          << ASC_dumpParameters(tempStr, m_params, ASC_ASSOC_AC));
 
-  /* count the presentation contexts which have been accepted by the SCP */
-  /* If there are none, finish the execution */
-  if (ASC_countAcceptedPresentationContexts(m_params) == 0)
-  {
-    DCMNET_ERROR("No Acceptable Presentation Contexts");
-    return NET_EC_NoAcceptablePresentationContexts;
-  }
+    /* count the presentation contexts which have been accepted by the SCP */
+    /* If there are none, finish the execution */
+    if (ASC_countAcceptedPresentationContexts(m_params) == 0)
+    {
+        DCMNET_ERROR("No Acceptable Presentation Contexts");
+        return NET_EC_NoAcceptablePresentationContexts;
+    }
 
-  /* dump general information concerning the establishment of the network connection if required */
-  DCMNET_INFO("Association Accepted (Max Send PDV: " << OFstatic_cast(unsigned long, m_assoc->sendPDVLength) << ")");
-  return EC_Normal;
+    /* dump general information concerning the establishment of the network connection if required */
+    DCMNET_INFO("Association Accepted (Max Send PDV: " << OFstatic_cast(unsigned long, m_assoc->sendPDVLength) << ")");
+    return EC_Normal;
 }
 
-
-OFCondition DcmSCU::addPresentationContext(const OFString &abstractSyntax,
-                                           const OFList<OFString> &xferSyntaxes,
+OFCondition DcmSCU::addPresentationContext(const OFString& abstractSyntax,
+                                           const OFList<OFString>& xferSyntaxes,
                                            const T_ASC_SC_ROLE role)
 
 {
 
-  DcmSCUPresContext presContext;
-  presContext.abstractSyntaxName = abstractSyntax;
-  OFListConstIterator(OFString) it = xferSyntaxes.begin();
-  OFListConstIterator(OFString) endOfList = xferSyntaxes.end();
-  while (it != endOfList)
-  {
-    presContext.transferSyntaxes.push_back(*it);
-    it++;
-  }
-  presContext.roleSelect = role;
-  m_presContexts.push_back(presContext);
-  return EC_Normal;
+    DcmSCUPresContext presContext;
+    presContext.abstractSyntaxName          = abstractSyntax;
+    OFListConstIterator(OFString) it        = xferSyntaxes.begin();
+    OFListConstIterator(OFString) endOfList = xferSyntaxes.end();
+    while (it != endOfList)
+    {
+        presContext.transferSyntaxes.push_back(*it);
+        it++;
+    }
+    presContext.roleSelect = role;
+    m_presContexts.push_back(presContext);
+    return EC_Normal;
 }
 
-
-OFCondition DcmSCU::useSecureConnection(DcmTransportLayer *tlayer)
+OFCondition DcmSCU::useSecureConnection(DcmTransportLayer* tlayer)
 {
-  OFCondition cond = ASC_setTransportLayer(m_net, tlayer, OFFalse /* do not take over ownership */);
-  if (cond.good())
-    cond = ASC_setTransportLayerType(m_params, OFTrue /* use TLS */);
-  return cond;
+    OFCondition cond = ASC_setTransportLayer(m_net, tlayer, OFFalse /* do not take over ownership */);
+    if (cond.good())
+        cond = ASC_setTransportLayerType(m_params, OFTrue /* use TLS */);
+    return cond;
 }
 
-
 void DcmSCU::clearPresentationContexts()
 {
-  m_presContexts.clear();
-  m_assocConfigFilename.clear();
-  m_assocConfigProfile.clear();
+    m_presContexts.clear();
+    m_assocConfigFilename.clear();
+    m_assocConfigProfile.clear();
 }
 
-
 // Returns usable presentation context ID for a given abstract syntax UID and
 // transfer syntax UID. 0 if none matches.
-T_ASC_PresentationContextID DcmSCU::findPresentationContextID(const OFString &abstractSyntax,
-                                                              const OFString &transferSyntax,
+T_ASC_PresentationContextID DcmSCU::findPresentationContextID(const OFStringabstractSyntax,
+                                                              const OFStringtransferSyntax,
                                                               const T_ASC_SC_ROLE requestorRole)
 {
-  if (!isConnected())
-    return 0;
+    if (!isConnected())
+        return 0;
 
-  DUL_PRESENTATIONCONTEXT *pc;
-  LST_HEAD **l;
-  OFBool found = OFFalse;
+    DUL_PRESENTATIONCONTEXT* pc;
+    LST_HEAD** l;
+    OFBool found = OFFalse;
 
-  if (abstractSyntax.empty()) return 0;
+    if (abstractSyntax.empty())
+        return 0;
 
-  /* first of all we look for a presentation context
-   * matching both abstract and transfer syntax
-   */
-  l = &m_assoc->params->DULparams.acceptedPresentationContext;
-  pc = (DUL_PRESENTATIONCONTEXT*) LST_Head(l);
-  (void)LST_Position(l, (LST_NODE*)pc);
-  while (pc && !found)
-  {
-    found = (strcmp(pc->abstractSyntax, abstractSyntax.c_str()) == 0);
-    found &= (pc->result == ASC_P_ACCEPTANCE);
-    if (!transferSyntax.empty())  // ignore transfer syntax if not specified
-      found &= (strcmp(pc->acceptedTransferSyntax, transferSyntax.c_str()) == 0);
-    if (found) found &= pc->acceptedSCRole == ascRole2dulRole(requestorRole);
-    if (!found) pc = (DUL_PRESENTATIONCONTEXT*) LST_Next(l);
-  }
-  if (found)
-    return pc->presentationContextID;
+    /* first of all we look for a presentation context
+     * matching both abstract and transfer syntax
+     */
+    l  = &m_assoc->params->DULparams.acceptedPresentationContext;
+    pc = (DUL_PRESENTATIONCONTEXT*)LST_Head(l);
+    (void)LST_Position(l, (LST_NODE*)pc);
+    while (pc && !found)
+    {
+        found = (strcmp(pc->abstractSyntax, abstractSyntax.c_str()) == 0);
+        found &= (pc->result == ASC_P_ACCEPTANCE);
+        if (!transferSyntax.empty()) // ignore transfer syntax if not specified
+            found &= (strcmp(pc->acceptedTransferSyntax, transferSyntax.c_str()) == 0);
+        if (found)
+            found &= pc->acceptedSCRole == ascRole2dulRole(requestorRole);
+        if (!found)
+            pc = (DUL_PRESENTATIONCONTEXT*)LST_Next(l);
+    }
+    if (found)
+        return pc->presentationContextID;
 
-  return 0;   /* not found */
+    return 0; /* not found */
 }
 
 // Returns the presentation context ID that best matches the given abstract syntax UID and
 // transfer syntax UID.
-T_ASC_PresentationContextID DcmSCU::findAnyPresentationContextID(const OFString &abstractSyntax,
-                                                                 const OFString &transferSyntax)
-{
-  if (m_assoc == NULL)
-    return 0;
-
-  DUL_PRESENTATIONCONTEXT *pc;
-  LST_HEAD **l;
-  OFBool found = OFFalse;
-
-  if (abstractSyntax.empty()) return 0;
-
-  /* first of all we look for a presentation context
-   * matching both abstract and transfer syntax
-   */
-  l = &m_assoc->params->DULparams.acceptedPresentationContext;
-  pc = (DUL_PRESENTATIONCONTEXT*) LST_Head(l);
-  (void)LST_Position(l, (LST_NODE*)pc);
-  while (pc && !found)
-  {
-    found = (strcmp(pc->abstractSyntax, abstractSyntax.c_str()) == 0);
-    found &= (pc->result == ASC_P_ACCEPTANCE);
-    if (!transferSyntax.empty())  // ignore transfer syntax if not specified
-      found &= (strcmp(pc->acceptedTransferSyntax, transferSyntax.c_str()) == 0);
-    if (!found) pc = (DUL_PRESENTATIONCONTEXT*) LST_Next(l);
-  }
-  if (found) return pc->presentationContextID;
-
-  /* now we look for an explicit VR uncompressed PC. */
-  l = &m_assoc->params->DULparams.acceptedPresentationContext;
-  pc = (DUL_PRESENTATIONCONTEXT*) LST_Head(l);
-  (void)LST_Position(l, (LST_NODE*)pc);
-  while (pc && !found)
-  {
-    found =  (strcmp(pc->abstractSyntax, abstractSyntax.c_str()) == 0)
-          && (pc->result == ASC_P_ACCEPTANCE)
-          && ((strcmp(pc->acceptedTransferSyntax, UID_LittleEndianExplicitTransferSyntax) == 0)
-          || (strcmp(pc->acceptedTransferSyntax, UID_BigEndianExplicitTransferSyntax) == 0));
-    if (!found) pc = (DUL_PRESENTATIONCONTEXT*) LST_Next(l);
-  }
-  if (found) return pc->presentationContextID;
-
-  /* now we look for an implicit VR uncompressed PC. */
-  l = &m_assoc->params->DULparams.acceptedPresentationContext;
-  pc = (DUL_PRESENTATIONCONTEXT*) LST_Head(l);
-  (void)LST_Position(l, (LST_NODE*)pc);
-  while (pc && !found)
-  {
-    found = (strcmp(pc->abstractSyntax, abstractSyntax.c_str()) == 0)
-          && (pc->result == ASC_P_ACCEPTANCE)
-          && (strcmp(pc->acceptedTransferSyntax, UID_LittleEndianImplicitTransferSyntax) == 0);
-    if (!found) pc = (DUL_PRESENTATIONCONTEXT*) LST_Next(l);
-  }
-  if (found) return pc->presentationContextID;
+T_ASC_PresentationContextID DcmSCU::findAnyPresentationContextID(const OFString& abstractSyntax,
+                                                                 const OFString& transferSyntax)
+{
+    if (m_assoc == NULL)
+        return 0;
+
+    DUL_PRESENTATIONCONTEXT* pc;
+    LST_HEAD** l;
+    OFBool found = OFFalse;
+
+    if (abstractSyntax.empty())
+        return 0;
+
+    /* first of all we look for a presentation context
+     * matching both abstract and transfer syntax
+     */
+    l  = &m_assoc->params->DULparams.acceptedPresentationContext;
+    pc = (DUL_PRESENTATIONCONTEXT*)LST_Head(l);
+    (void)LST_Position(l, (LST_NODE*)pc);
+    while (pc && !found)
+    {
+        found = (strcmp(pc->abstractSyntax, abstractSyntax.c_str()) == 0);
+        found &= (pc->result == ASC_P_ACCEPTANCE);
+        if (!transferSyntax.empty()) // ignore transfer syntax if not specified
+            found &= (strcmp(pc->acceptedTransferSyntax, transferSyntax.c_str()) == 0);
+        if (!found)
+            pc = (DUL_PRESENTATIONCONTEXT*)LST_Next(l);
+    }
+    if (found)
+        return pc->presentationContextID;
+
+    /* now we look for an explicit VR uncompressed PC. */
+    l  = &m_assoc->params->DULparams.acceptedPresentationContext;
+    pc = (DUL_PRESENTATIONCONTEXT*)LST_Head(l);
+    (void)LST_Position(l, (LST_NODE*)pc);
+    while (pc && !found)
+    {
+        found = (strcmp(pc->abstractSyntax, abstractSyntax.c_str()) == 0) && (pc->result == ASC_P_ACCEPTANCE)
+            && ((strcmp(pc->acceptedTransferSyntax, UID_LittleEndianExplicitTransferSyntax) == 0)
+                || (strcmp(pc->acceptedTransferSyntax, UID_BigEndianExplicitTransferSyntax) == 0));
+        if (!found)
+            pc = (DUL_PRESENTATIONCONTEXT*)LST_Next(l);
+    }
+    if (found)
+        return pc->presentationContextID;
+
+    /* now we look for an implicit VR uncompressed PC. */
+    l  = &m_assoc->params->DULparams.acceptedPresentationContext;
+    pc = (DUL_PRESENTATIONCONTEXT*)LST_Head(l);
+    (void)LST_Position(l, (LST_NODE*)pc);
+    while (pc && !found)
+    {
+        found = (strcmp(pc->abstractSyntax, abstractSyntax.c_str()) == 0) && (pc->result == ASC_P_ACCEPTANCE)
+            && (strcmp(pc->acceptedTransferSyntax, UID_LittleEndianImplicitTransferSyntax) == 0);
+        if (!found)
+            pc = (DUL_PRESENTATIONCONTEXT*)LST_Next(l);
+    }
+    if (found)
+        return pc->presentationContextID;
 
-  /* finally we accept everything we get.
-     returns 0 if abstract syntax is not supported
-  */
-  return ASC_findAcceptedPresentationContextID(m_assoc, abstractSyntax.c_str());
+    /* finally we accept everything we get.
+       returns 0 if abstract syntax is not supported
+    */
+    return ASC_findAcceptedPresentationContextID(m_assoc, abstractSyntax.c_str());
 }
 
 void DcmSCU::findPresentationContext(const T_ASC_PresentationContextID presID,
-                                     OFString &abstractSyntax,
-                                     OFString &transferSyntax)
-{
-  transferSyntax.clear();
-  abstractSyntax.clear();
-  if (m_assoc == NULL)
-    return;
-
-  DUL_PRESENTATIONCONTEXT *pc;
-  LST_HEAD **l;
-
-  /* we look for a presentation context matching
-   * both abstract and transfer syntax
-   */
-  l = &m_assoc->params->DULparams.acceptedPresentationContext;
-  pc = (DUL_PRESENTATIONCONTEXT*) LST_Head(l);
-  (void)LST_Position(l, (LST_NODE*)pc);
-  while (pc)
-  {
-    if (presID == pc->presentationContextID)
+                                     OFString& abstractSyntax,
+                                     OFString& transferSyntax)
+{
+    transferSyntax.clear();
+    abstractSyntax.clear();
+    if (m_assoc == NULL)
+        return;
+
+    DUL_PRESENTATIONCONTEXT* pc;
+    LST_HEAD** l;
+
+    /* we look for a presentation context matching
+     * both abstract and transfer syntax
+     */
+    l  = &m_assoc->params->DULparams.acceptedPresentationContext;
+    pc = (DUL_PRESENTATIONCONTEXT*)LST_Head(l);
+    (void)LST_Position(l, (LST_NODE*)pc);
+    while (pc)
     {
-      if (pc->result == ASC_P_ACCEPTANCE)
-      {
-        // found a match
-        transferSyntax = pc->acceptedTransferSyntax;
-        abstractSyntax = pc->abstractSyntax;
-      }
-      break;
+        if (presID == pc->presentationContextID)
+        {
+            if (pc->result == ASC_P_ACCEPTANCE)
+            {
+                // found a match
+                transferSyntax = pc->acceptedTransferSyntax;
+                abstractSyntax = pc->abstractSyntax;
+            }
+            break;
+        }
+        pc = (DUL_PRESENTATIONCONTEXT*)LST_Next(l);
     }
-    pc = (DUL_PRESENTATIONCONTEXT*) LST_Next(l);
-  }
 }
 
-
 Uint16 DcmSCU::nextMessageID()
 {
-  if (!isConnected())
-    return 0;
-  else
-    return m_assoc->nextMsgID++;
+    if (!isConnected())
+        return 0;
+    else
+        return m_assoc->nextMsgID++;
 }
 
-
 void DcmSCU::closeAssociation(const DcmCloseAssociationType closeType)
 {
-  if (!isConnected())
-  {
-    DCMNET_WARN("Closing of association requested but no association active (ignored)");
-    return;
-  }
+    if (!isConnected())
+    {
+        DCMNET_WARN("Closing of association requested but no association active (ignored)");
+        return;
+    }
 
-  OFCondition cond;
-  OFString tempStr;
+    OFCondition cond;
+    OFString tempStr;
 
-  /* tear down association, i.e. terminate network connection to SCP */
-  switch (closeType)
-  {
-    case DCMSCU_RELEASE_ASSOCIATION:
-      /* release association */
-      DCMNET_INFO("Releasing Association");
-      cond = ASC_releaseAssociation(m_assoc);
-      if (cond.bad())
-      {
-        DCMNET_ERROR("Association Release Failed: " << DimseCondition::dump(tempStr, cond));
-        return; // TODO: do we really need this?
-      }
-      break;
-    case DCMSCU_ABORT_ASSOCIATION:
-      /* abort association */
-      DCMNET_INFO("Aborting Association");
-      cond = ASC_abortAssociation(m_assoc);
-      if (cond.bad())
-      {
-        DCMNET_ERROR("Association Abort Failed: " << DimseCondition::dump(tempStr, cond));
-      }
-      break;
-    case DCMSCU_PEER_REQUESTED_RELEASE:
-      /* peer requested release */
-      DCMNET_ERROR("Protocol Error: Peer requested release (Aborting)");
-      DCMNET_INFO("Aborting Association");
-      cond = ASC_abortAssociation(m_assoc);
-      if (cond.bad())
-      {
-        DCMNET_ERROR("Association Abort Failed: " << DimseCondition::dump(tempStr, cond));
-      }
-      break;
-    case DCMSCU_PEER_ABORTED_ASSOCIATION:
-      /* peer aborted association */
-      DCMNET_INFO("Peer Aborted Association");
-      break;
-  }
+    /* tear down association, i.e. terminate network connection to SCP */
+    switch (closeType)
+    {
+        case DCMSCU_RELEASE_ASSOCIATION:
+            /* release association */
+            DCMNET_INFO("Releasing Association");
+            cond = ASC_releaseAssociation(m_assoc);
+            if (cond.bad())
+            {
+                DCMNET_ERROR("Association Release Failed: " << DimseCondition::dump(tempStr, cond));
+                return; // TODO: do we really need this?
+            }
+            break;
+        case DCMSCU_ABORT_ASSOCIATION:
+            /* abort association */
+            DCMNET_INFO("Aborting Association");
+            cond = ASC_abortAssociation(m_assoc);
+            if (cond.bad())
+            {
+                DCMNET_ERROR("Association Abort Failed: " << DimseCondition::dump(tempStr, cond));
+            }
+            break;
+        case DCMSCU_PEER_REQUESTED_RELEASE:
+            /* peer requested release */
+            DCMNET_ERROR("Protocol Error: Peer requested release (Aborting)");
+            DCMNET_INFO("Aborting Association");
+            cond = ASC_abortAssociation(m_assoc);
+            if (cond.bad())
+            {
+                DCMNET_ERROR("Association Abort Failed: " << DimseCondition::dump(tempStr, cond));
+            }
+            break;
+        case DCMSCU_PEER_ABORTED_ASSOCIATION:
+            /* peer aborted association */
+            DCMNET_INFO("Peer Aborted Association");
+            break;
+    }
 
-  // destroy and free memory of internal association and network structures
-  freeNetwork();
+    // destroy and free memory of internal association and network structures
+    freeNetwork();
 }
 
-
 OFCondition DcmSCU::releaseAssociation()
 {
     OFCondition status = DIMSE_ILLEGALASSOCIATION;
@@ -553,7 +559,6 @@ OFCondition DcmSCU::releaseAssociation()
     return status;
 }
 
-
 OFCondition DcmSCU::abortAssociation()
 {
     OFCondition status = DIMSE_ILLEGALASSOCIATION;
@@ -566,7 +571,6 @@ OFCondition DcmSCU::abortAssociation()
     return status;
 }
 
-
 /* ************************************************************************* */
 /*                            C-ECHO functionality                           */
 /* ************************************************************************* */
@@ -574,92 +578,99 @@ OFCondition DcmSCU::abortAssociation()
 // Sends C-ECHO request to another DICOM application
 OFCondition DcmSCU::sendECHORequest(const T_ASC_PresentationContextID presID)
 {
-  if (!isConnected())
-    return DIMSE_ILLEGALASSOCIATION;
+    if (!isConnected())
+        return DIMSE_ILLEGALASSOCIATION;
 
-  OFCondition cond;
-  T_ASC_PresentationContextID pcid = presID;
+    OFCondition cond;
+    T_ASC_PresentationContextID pcid = presID;
 
-  /* If necessary, find appropriate presentation context */
-  if (pcid == 0)
-    pcid = findPresentationContextID(UID_VerificationSOPClass, UID_LittleEndianExplicitTransferSyntax);
-  if (pcid == 0)
-    pcid = findPresentationContextID(UID_VerificationSOPClass, UID_BigEndianExplicitTransferSyntax);
-  if (pcid == 0)
-    pcid = findPresentationContextID(UID_VerificationSOPClass, UID_LittleEndianImplicitTransferSyntax);
-  if (pcid == 0)
-  {
-    DCMNET_ERROR("No valid presentation context found for sending C-ECHO using SOP Class: "  << dcmFindNameOfUID(UID_VerificationSOPClass, "")) ;
-    return DIMSE_NOVALIDPRESENTATIONCONTEXTID;
-  }
+    /* If necessary, find appropriate presentation context */
+    if (pcid == 0)
+        pcid = findPresentationContextID(UID_VerificationSOPClass, UID_LittleEndianExplicitTransferSyntax);
+    if (pcid == 0)
+        pcid = findPresentationContextID(UID_VerificationSOPClass, UID_BigEndianExplicitTransferSyntax);
+    if (pcid == 0)
+        pcid = findPresentationContextID(UID_VerificationSOPClass, UID_LittleEndianImplicitTransferSyntax);
+    if (pcid == 0)
+    {
+        DCMNET_ERROR("No valid presentation context found for sending C-ECHO using SOP Class: "
+                     << dcmFindNameOfUID(UID_VerificationSOPClass, ""));
+        return DIMSE_NOVALIDPRESENTATIONCONTEXTID;
+    }
 
-  /* Now, assemble DIMSE message */
-  T_DIMSE_Message msg;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&msg, sizeof(msg));
-  T_DIMSE_C_EchoRQ* req = &(msg.msg.CEchoRQ);
-  // Set type of message
-  msg.CommandField = DIMSE_C_ECHO_RQ;
-  // Set message ID
-  req->MessageID = nextMessageID();
-  // Announce no dataset
-  req->DataSetType = DIMSE_DATASET_NULL;
-  // Set affected SOP Class UID (always Verification SOP Class)
-  OFStandard::strlcpy(req->AffectedSOPClassUID, UID_VerificationSOPClass, sizeof(req->AffectedSOPClassUID));
-
-  /* Send request */
-  OFString tempStr;
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-  {
-    DCMNET_INFO("Sending C-ECHO Request");
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, msg, DIMSE_OUTGOING, NULL, pcid));
-  } else {
-    DCMNET_INFO("Sending C-ECHO Request (MsgID " << req->MessageID << ")");
-  }
-  cond = sendDIMSEMessage(pcid, &msg, NULL /*dataObject*/);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed sending C-ECHO request: " << DimseCondition::dump(tempStr, cond));
-    return cond;
-  }
+    /* Now, assemble DIMSE message */
+    T_DIMSE_Message msg;
+    // Make sure everything is zeroed (especially options)
+    bzero((char*)&msg, sizeof(msg));
+    T_DIMSE_C_EchoRQ* req = &(msg.msg.CEchoRQ);
+    // Set type of message
+    msg.CommandField = DIMSE_C_ECHO_RQ;
+    // Set message ID
+    req->MessageID = nextMessageID();
+    // Announce no dataset
+    req->DataSetType = DIMSE_DATASET_NULL;
+    // Set affected SOP Class UID (always Verification SOP Class)
+    OFStandard::strlcpy(req->AffectedSOPClassUID, UID_VerificationSOPClass, sizeof(req->AffectedSOPClassUID));
+
+    /* Send request */
+    OFString tempStr;
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+    {
+        DCMNET_INFO("Sending C-ECHO Request");
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, msg, DIMSE_OUTGOING, NULL, pcid));
+    }
+    else
+    {
+        DCMNET_INFO("Sending C-ECHO Request (MsgID " << req->MessageID << ")");
+    }
+    cond = sendDIMSEMessage(pcid, &msg, NULL /*dataObject*/);
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Failed sending C-ECHO request: " << DimseCondition::dump(tempStr, cond));
+        return cond;
+    }
 
-  /* Receive response */
-  T_DIMSE_Message rsp;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&rsp, sizeof(rsp));
+    /* Receive response */
+    T_DIMSE_Message rsp;
+    // Make sure everything is zeroed (especially options)
+    bzero((char*)&rsp, sizeof(rsp));
 
-  DcmDataset* statusDetail = NULL;
-  cond = receiveDIMSECommand(&pcid, &rsp, &statusDetail, NULL /* not interested in the command set */);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed receiving DIMSE response: " << DimseCondition::dump(tempStr, cond));
-    return cond;
-  }
-  /* Check whether we received C-ECHO response, otherwise print error */
-  if (rsp.CommandField == DIMSE_C_ECHO_RSP)
-  {
-    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+    DcmDataset* statusDetail = NULL;
+    cond = receiveDIMSECommand(&pcid, &rsp, &statusDetail, NULL /* not interested in the command set */);
+    if (cond.bad())
     {
-      DCMNET_INFO("Received C-ECHO Response");
-      DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
-    } else {
-      DCMNET_INFO("Received C-ECHO Response (" << DU_cechoStatusString(rsp.msg.CEchoRSP.DimseStatus) << ")");
-    }
-  } else {
-    DCMNET_ERROR("Expected C-ECHO response but received DIMSE command 0x"
-      << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
-      << OFstatic_cast(unsigned int, rsp.CommandField));
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
-    delete statusDetail;
-    return DIMSE_BADCOMMANDTYPE;
-  }
-  /* Print status detail if it was received */
-  if (statusDetail != NULL)
-  {
-    DCMNET_DEBUG("Response has status detail:" << OFendl << DcmObject::PrintHelper(*statusDetail));
-    delete statusDetail;
-  }
-  return EC_Normal;
+        DCMNET_ERROR("Failed receiving DIMSE response: " << DimseCondition::dump(tempStr, cond));
+        return cond;
+    }
+    /* Check whether we received C-ECHO response, otherwise print error */
+    if (rsp.CommandField == DIMSE_C_ECHO_RSP)
+    {
+        if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+        {
+            DCMNET_INFO("Received C-ECHO Response");
+            DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
+        }
+        else
+        {
+            DCMNET_INFO("Received C-ECHO Response (" << DU_cechoStatusString(rsp.msg.CEchoRSP.DimseStatus) << ")");
+        }
+    }
+    else
+    {
+        DCMNET_ERROR("Expected C-ECHO response but received DIMSE command 0x"
+                     << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
+                     << OFstatic_cast(unsigned int, rsp.CommandField));
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
+        delete statusDetail;
+        return DIMSE_BADCOMMANDTYPE;
+    }
+    /* Print status detail if it was received */
+    if (statusDetail != NULL)
+    {
+        DCMNET_DEBUG("Response has status detail:" << OFendl << DcmObject::PrintHelper(*statusDetail));
+        delete statusDetail;
+    }
+    return EC_Normal;
 }
 
 /* ************************************************************************* */
@@ -668,1022 +679,931 @@ OFCondition DcmSCU::sendECHORequest(const T_ASC_PresentationContextID presID)
 
 // Sends C-STORE request to another DICOM application
 OFCondition DcmSCU::sendSTORERequest(const T_ASC_PresentationContextID presID,
-                                     const OFFilename &dicomFile,
-                                     DcmDataset *dataset,
-                                     Uint16 &rspStatusCode,
-                                     const OFString &moveOriginatorAETitle,
+                                     const OFFilenamedicomFile,
+                                     DcmDatasetdataset,
+                                     Uint16rspStatusCode,
+                                     const OFStringmoveOriginatorAETitle,
                                      const Uint16 moveOriginatorMsgID)
 {
-  // Do some basic validity checks
-  if (!isConnected())
-    return DIMSE_ILLEGALASSOCIATION;
-
-  OFCondition cond;
-  OFString tempStr;
-  T_ASC_PresentationContextID pcid = presID;
-  DcmDataset* statusDetail = NULL;
-  T_DIMSE_Message msg;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&msg, sizeof(msg));
-  T_DIMSE_C_StoreRQ* req = &(msg.msg.CStoreRQ);
-
-  // Set type of message
-  msg.CommandField = DIMSE_C_STORE_RQ;
-  /* Set message ID */
-  req->MessageID = nextMessageID();
-  /* Load file if necessary */
-  DcmFileFormat *fileformat = NULL;
-  if (!dicomFile.isEmpty())
-  {
-    fileformat = new DcmFileFormat();
-    if (fileformat == NULL)
-      return EC_MemoryExhausted;
-    cond = fileformat->loadFile(dicomFile);
-    if (cond.bad())
-    {
-      delete fileformat;
-      return cond;
-    }
-    dataset = fileformat->getDataset();
-  }
+    // Do some basic validity checks
+    if (!isConnected())
+        return DIMSE_ILLEGALASSOCIATION;
 
-  /* Fill message according to dataset to be sent */
-  OFString sopClassUID;
-  OFString sopInstanceUID;
-  E_TransferSyntax xferSyntax = EXS_Unknown;
-  cond = getDatasetInfo(dataset, sopClassUID, sopInstanceUID, xferSyntax);
-  DcmXfer xfer(xferSyntax);
-  /* Check whether the information is sufficient */
-  if (sopClassUID.empty() || sopInstanceUID.empty() || ((pcid == 0) && (xferSyntax == EXS_Unknown)))
-  {
-    DCMNET_ERROR("Cannot send SOP instance, missing information:");
+    OFCondition cond;
+    OFString tempStr;
+    T_ASC_PresentationContextID pcid = presID;
+    DcmDataset* statusDetail         = NULL;
+    T_DIMSE_Message msg;
+    // Make sure everything is zeroed (especially options)
+    bzero((char*)&msg, sizeof(msg));
+    T_DIMSE_C_StoreRQ* req = &(msg.msg.CStoreRQ);
+
+    // Set type of message
+    msg.CommandField = DIMSE_C_STORE_RQ;
+    /* Set message ID */
+    req->MessageID = nextMessageID();
+    /* Load file if necessary */
+    DcmFileFormat* fileformat = NULL;
     if (!dicomFile.isEmpty())
-      DCMNET_ERROR("  DICOM Filename   : " << dicomFile);
-    DCMNET_ERROR("  SOP Class UID    : " << sopClassUID);
-    DCMNET_ERROR("  SOP Instance UID : " << sopInstanceUID);
-    DCMNET_ERROR("  Transfer Syntax  : " << xfer.getXferName());
-    if (pcid == 0)
-      DCMNET_ERROR("  Pres. Context ID : 0 (find via SOP Class and Transfer Syntax)");
-    else
-      DCMNET_ERROR("  Pres. Context ID : " << OFstatic_cast(unsigned int, pcid));
-    delete fileformat;
-    return cond;
-  }
-  OFStandard::strlcpy(req->AffectedSOPClassUID, sopClassUID.c_str(), sizeof(req->AffectedSOPClassUID));
-  OFStandard::strlcpy(req->AffectedSOPInstanceUID, sopInstanceUID.c_str(), sizeof(req->AffectedSOPInstanceUID));
-  req->DataSetType = DIMSE_DATASET_PRESENT;
-  req->Priority = DIMSE_PRIORITY_MEDIUM;
-
-  /* If desired (optional), insert MOVE originator information if this C-STORE
-     was initiated through a C-MOVE request.
-   */
-  if (!moveOriginatorAETitle.empty())
-  {
-    OFStandard::strlcpy(req->MoveOriginatorApplicationEntityTitle, moveOriginatorAETitle.c_str(), sizeof(req->MoveOriginatorApplicationEntityTitle));
-    req->opts |= O_STORE_MOVEORIGINATORAETITLE;
-  }
-  if (moveOriginatorMsgID != 0)
-  {
-    req->MoveOriginatorID = moveOriginatorMsgID;
-    req->opts |= O_STORE_MOVEORIGINATORID;
-  }
-
-  /* If no presentation context is specified by the caller ... */
-  if (pcid == 0)
-  {
-      /* ... try to find an appropriate presentation context automatically */
-    pcid = findPresentationContextID(sopClassUID, xfer.getXferID());
-  }
-  else if (m_datasetConversionMode)
-  {
-    /* Convert dataset to network transfer syntax (if required) */
-    OFString abstractSyntax, transferSyntax;
-    findPresentationContext(pcid, abstractSyntax, transferSyntax);
-    /* Check whether given presentation context was accepted by the peer */
-    if (abstractSyntax.empty() || transferSyntax.empty())
     {
-      /* Mark presentation context as invalid */
-      pcid = 0;
-    } else {
-      if (abstractSyntax != sopClassUID)
-      {
-        DCMNET_WARN("Inappropriate presentation context with ID " << OFstatic_cast(unsigned int, pcid)
-          << ": abstract syntax does not match SOP class UID");
-      }
-      /* Try to convert to the negotiated transfer syntax */
-      DcmXfer netXfer = DcmXfer(transferSyntax.c_str()).getXfer();
-      if (netXfer.getXfer() != xferSyntax)
-      {
-        DCMNET_INFO("Converting transfer syntax: " << xfer.getXferName() << " -> "
-          << netXfer.getXferName());
-        cond = dataset->chooseRepresentation(netXfer.getXfer(), NULL);
+        fileformat = new DcmFileFormat();
+        if (fileformat == NULL)
+            return EC_MemoryExhausted;
+        cond = fileformat->loadFile(dicomFile);
         if (cond.bad())
         {
-           DCMNET_ERROR("No conversion to transfer syntax " << netXfer.getXferName() << " possible!");
-           delete fileformat;
-           return cond;
+            delete fileformat;
+            return cond;
         }
-      }
+        dataset = fileformat->getDataset();
     }
-  }
-  /* No appropriate presentation context for sending */
-  if (pcid == 0)
-  {
-    OFString sopClassName = dcmFindNameOfUID(sopClassUID.c_str(), sopClassUID.c_str());
-    OFString xferName = xfer.getXferName();
-    DCMNET_ERROR("No presentation context found for sending C-STORE with SOP Class / Transfer Syntax: "
-      << sopClassName << " / " << xferName);
-    delete fileformat;
-    return DIMSE_NOVALIDPRESENTATIONCONTEXTID;
-  }
-
-  /* Send request */
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-  {
-    DCMNET_INFO("Sending C-STORE Request");
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, msg, DIMSE_OUTGOING, NULL, pcid));
-  } else {
-    DCMNET_INFO("Sending C-STORE Request (MsgID " << req->MessageID << ", "
-      << dcmSOPClassUIDToModality(sopClassUID.c_str(), "OT") << ")");
-  }
-  cond = sendDIMSEMessage(pcid, &msg, dataset);
-  delete fileformat;
-  fileformat = NULL;
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed sending C-STORE request: " << DimseCondition::dump(tempStr, cond));
-    return cond;
-  }
-
-  /* Receive response */
-  T_DIMSE_Message rsp;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&rsp, sizeof(rsp));
-  cond = receiveDIMSECommand(&pcid, &rsp, &statusDetail, NULL /* not interested in the command set */);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed receiving DIMSE response: " << DimseCondition::dump(tempStr, cond));
-    return cond;
-  }
 
-  if (rsp.CommandField == DIMSE_C_STORE_RSP)
-  {
-    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+    /* Fill message according to dataset to be sent */
+    OFString sopClassUID;
+    OFString sopInstanceUID;
+    E_TransferSyntax xferSyntax = EXS_Unknown;
+    cond                        = getDatasetInfo(dataset, sopClassUID, sopInstanceUID, xferSyntax);
+    DcmXfer xfer(xferSyntax);
+    /* Check whether the information is sufficient */
+    if (sopClassUID.empty() || sopInstanceUID.empty() || ((pcid == 0) && (xferSyntax == EXS_Unknown)))
     {
-      DCMNET_INFO("Received C-STORE Response");
-      DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
-    } else {
-      DCMNET_INFO("Received C-STORE Response (" << DU_cstoreStatusString(rsp.msg.CStoreRSP.DimseStatus) << ")");
-    }
-  } else {
-    DCMNET_ERROR("Expected C-STORE response but received DIMSE command 0x"
-      << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
-      << OFstatic_cast(unsigned int, rsp.CommandField));
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
-    delete statusDetail;
-    return DIMSE_BADCOMMANDTYPE;
-  }
-  T_DIMSE_C_StoreRSP storeRsp = rsp.msg.CStoreRSP;
-  rspStatusCode = storeRsp.DimseStatus;
-  if (statusDetail != NULL)
-  {
-    DCMNET_DEBUG("Response has status detail:" << OFendl << DcmObject::PrintHelper(*statusDetail));
-    delete statusDetail;
-  }
-
-  return cond;
-}
-
+        DCMNET_ERROR("Cannot send SOP instance, missing information:");
+        if (!dicomFile.isEmpty())
+            DCMNET_ERROR("  DICOM Filename   : " << dicomFile);
+        DCMNET_ERROR("  SOP Class UID    : " << sopClassUID);
+        DCMNET_ERROR("  SOP Instance UID : " << sopInstanceUID);
+        DCMNET_ERROR("  Transfer Syntax  : " << xfer.getXferName());
+        if (pcid == 0)
+            DCMNET_ERROR("  Pres. Context ID : 0 (find via SOP Class and Transfer Syntax)");
+        else
+            DCMNET_ERROR("  Pres. Context ID : " << OFstatic_cast(unsigned int, pcid));
+        delete fileformat;
+        return cond;
+    }
+    OFStandard::strlcpy(req->AffectedSOPClassUID, sopClassUID.c_str(), sizeof(req->AffectedSOPClassUID));
+    OFStandard::strlcpy(req->AffectedSOPInstanceUID, sopInstanceUID.c_str(), sizeof(req->AffectedSOPInstanceUID));
+    req->DataSetType = DIMSE_DATASET_PRESENT;
+    req->Priority    = DIMSE_PRIORITY_MEDIUM;
+
+    /* If desired (optional), insert MOVE originator information if this C-STORE
+       was initiated through a C-MOVE request.
+     */
+    if (!moveOriginatorAETitle.empty())
+    {
+        OFStandard::strlcpy(req->MoveOriginatorApplicationEntityTitle,
+                            moveOriginatorAETitle.c_str(),
+                            sizeof(req->MoveOriginatorApplicationEntityTitle));
+        req->opts |= O_STORE_MOVEORIGINATORAETITLE;
+    }
+    if (moveOriginatorMsgID != 0)
+    {
+        req->MoveOriginatorID = moveOriginatorMsgID;
+        req->opts |= O_STORE_MOVEORIGINATORID;
+    }
 
-/* ************************************************************************* */
-/*                            C-MOVE functionality                           */
-/* ************************************************************************* */
+    /* If no presentation context is specified by the caller ... */
+    if (pcid == 0)
+    {
+        /* ... try to find an appropriate presentation context automatically */
+        pcid = findPresentationContextID(sopClassUID, xfer.getXferID());
+    }
+    else if (m_datasetConversionMode)
+    {
+        /* Convert dataset to network transfer syntax (if required) */
+        OFString abstractSyntax, transferSyntax;
+        findPresentationContext(pcid, abstractSyntax, transferSyntax);
+        /* Check whether given presentation context was accepted by the peer */
+        if (abstractSyntax.empty() || transferSyntax.empty())
+        {
+            /* Mark presentation context as invalid */
+            pcid = 0;
+        }
+        else
+        {
+            if (abstractSyntax != sopClassUID)
+            {
+                DCMNET_WARN("Inappropriate presentation context with ID "
+                            << OFstatic_cast(unsigned int, pcid) << ": abstract syntax does not match SOP class UID");
+            }
+            /* Try to convert to the negotiated transfer syntax */
+            DcmXfer netXfer = DcmXfer(transferSyntax.c_str()).getXfer();
+            if (netXfer.getXfer() != xferSyntax)
+            {
+                DCMNET_INFO("Converting transfer syntax: " << xfer.getXferName() << " -> " << netXfer.getXferName());
+                cond = dataset->chooseRepresentation(netXfer.getXfer(), NULL);
+                if (cond.bad())
+                {
+                    DCMNET_ERROR("No conversion to transfer syntax " << netXfer.getXferName() << " possible!");
+                    delete fileformat;
+                    return cond;
+                }
+            }
+        }
+    }
+    /* No appropriate presentation context for sending */
+    if (pcid == 0)
+    {
+        OFString sopClassName = dcmFindNameOfUID(sopClassUID.c_str(), sopClassUID.c_str());
+        OFString xferName     = xfer.getXferName();
+        DCMNET_ERROR("No presentation context found for sending C-STORE with SOP Class / Transfer Syntax: "
+                     << sopClassName << " / " << xferName);
+        delete fileformat;
+        return DIMSE_NOVALIDPRESENTATIONCONTEXTID;
+    }
 
-// Sends a C-MOVE Request on given presentation context
-OFCondition DcmSCU::sendMOVERequest(const T_ASC_PresentationContextID presID,
-                                    const OFString &moveDestinationAETitle,
-                                    DcmDataset *dataset,
-                                    OFList<RetrieveResponse*> *responses)
-{
-  // Do some basic validity checks
-  if (!isConnected())
-    return DIMSE_ILLEGALASSOCIATION;
-  if (dataset == NULL)
-    return DIMSE_NULLKEY;
-
-  /* Prepare DIMSE data structures for issuing request */
-  OFCondition cond;
-  OFString tempStr;
-  T_ASC_PresentationContextID pcid = presID;
-  T_DIMSE_Message msg;
-  // make sure everything is zeroed (especially options)
-  bzero((char*)&msg, sizeof(msg));
-  DcmDataset* statusDetail = NULL;
-  T_DIMSE_C_MoveRQ* req = &(msg.msg.CMoveRQ);
-  // Set type of message
-  msg.CommandField = DIMSE_C_MOVE_RQ;
-  // Set message ID
-  req->MessageID = nextMessageID();
-  // Announce dataset
-  req->DataSetType = DIMSE_DATASET_PRESENT;
-  // Set target for embedded C-Store's
-  OFStandard::strlcpy(req->MoveDestination, moveDestinationAETitle.c_str(), sizeof(req->MoveDestination));
-  // Set priority (mandatory)
-  req->Priority = DIMSE_PRIORITY_MEDIUM;
-
-  /* Determine SOP Class from presentation context */
-  OFString abstractSyntax, transferSyntax;
-  findPresentationContext(pcid, abstractSyntax, transferSyntax);
-  if (abstractSyntax.empty() || transferSyntax.empty())
-    return DIMSE_NOVALIDPRESENTATIONCONTEXTID;
-  OFStandard::strlcpy(req->AffectedSOPClassUID, abstractSyntax.c_str(), sizeof(req->AffectedSOPClassUID));
-
-  /* Send request */
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-  {
-    DCMNET_INFO("Sending C-MOVE Request");
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, msg, DIMSE_OUTGOING, dataset, pcid));
-  } else {
-    DCMNET_INFO("Sending C-MOVE Request (MsgID " << req->MessageID << ")");
-  }
-  cond = sendDIMSEMessage(pcid, &msg, dataset);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed sending C-MOVE request: " << DimseCondition::dump(tempStr, cond));
-    return cond;
-  }
+    /* Send request */
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+    {
+        DCMNET_INFO("Sending C-STORE Request");
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, msg, DIMSE_OUTGOING, NULL, pcid));
+    }
+    else
+    {
+        DCMNET_INFO("Sending C-STORE Request (MsgID " << req->MessageID << ", "
+                                                      << dcmSOPClassUIDToModality(sopClassUID.c_str(), "OT") << ")");
+    }
+    cond = sendDIMSEMessage(pcid, &msg, dataset);
+    delete fileformat;
+    fileformat = NULL;
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Failed sending C-STORE request: " << DimseCondition::dump(tempStr, cond));
+        return cond;
+    }
 
-  /* Receive and handle C-MOVE response messages */
-  OFBool waitForNextResponse = OFTrue;
-  while (waitForNextResponse)
-  {
+    /* Receive response */
     T_DIMSE_Message rsp;
-    // Make sure everything is zeroed, especially options
+    // Make sure everything is zeroed (especially options)
     bzero((char*)&rsp, sizeof(rsp));
-    statusDetail = NULL;
-
-    // Receive command set
     cond = receiveDIMSECommand(&pcid, &rsp, &statusDetail, NULL /* not interested in the command set */);
     if (cond.bad())
     {
-      DCMNET_ERROR("Failed receiving DIMSE response: " << DimseCondition::dump(tempStr, cond));
-      delete statusDetail;
-      break;
+        DCMNET_ERROR("Failed receiving DIMSE response: " << DimseCondition::dump(tempStr, cond));
+        return cond;
     }
 
-    if (rsp.CommandField == DIMSE_C_MOVE_RSP)
+    if (rsp.CommandField == DIMSE_C_STORE_RSP)
     {
-      if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-      {
-        DCMNET_INFO("Received C-MOVE Response");
+        if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+        {
+            DCMNET_INFO("Received C-STORE Response");
+            DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
+        }
+        else
+        {
+            DCMNET_INFO("Received C-STORE Response (" << DU_cstoreStatusString(rsp.msg.CStoreRSP.DimseStatus) << ")");
+        }
+    }
+    else
+    {
+        DCMNET_ERROR("Expected C-STORE response but received DIMSE command 0x"
+                     << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
+                     << OFstatic_cast(unsigned int, rsp.CommandField));
         DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
-      } else {
-        DCMNET_INFO("Received C-MOVE Response (" << DU_cmoveStatusString(rsp.msg.CMoveRSP.DimseStatus) << ")");
-      }
-    } else {
-      DCMNET_ERROR("Expected C-MOVE response but received DIMSE command 0x"
-        << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
-        << OFstatic_cast(unsigned int, rsp.CommandField));
-      DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
-      delete statusDetail;
-      cond = DIMSE_BADCOMMANDTYPE;
-      break;
-    }
-
-    // Prepare response package for response handler
-    OFunique_ptr<RetrieveResponse> moveRSP(new RetrieveResponse);
-    moveRSP->m_affectedSOPClassUID = rsp.msg.CMoveRSP.AffectedSOPClassUID;
-    moveRSP->m_messageIDRespondedTo = rsp.msg.CMoveRSP.MessageIDBeingRespondedTo;
-    moveRSP->m_status = rsp.msg.CMoveRSP.DimseStatus;
-    moveRSP->m_numberOfRemainingSubops = rsp.msg.CMoveRSP.NumberOfRemainingSubOperations;
-    moveRSP->m_numberOfCompletedSubops = rsp.msg.CMoveRSP.NumberOfCompletedSubOperations;
-    moveRSP->m_numberOfFailedSubops = rsp.msg.CMoveRSP.NumberOfFailedSubOperations;
-    moveRSP->m_numberOfWarningSubops = rsp.msg.CMoveRSP.NumberOfWarningSubOperations;
-    moveRSP->m_statusDetail = statusDetail;
-    //DCMNET_DEBUG("C-MOVE response has status 0x"
-    //  << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
-    //  << moveRSP->m_status);
+        delete statusDetail;
+        return DIMSE_BADCOMMANDTYPE;
+    }
+    T_DIMSE_C_StoreRSP storeRsp = rsp.msg.CStoreRSP;
+    rspStatusCode               = storeRsp.DimseStatus;
     if (statusDetail != NULL)
     {
-      DCMNET_DEBUG("Response has status detail:" << OFendl << DcmObject::PrintHelper(*statusDetail));
+        DCMNET_DEBUG("Response has status detail:" << OFendl << DcmObject::PrintHelper(*statusDetail));
+        delete statusDetail;
     }
 
-    // Receive dataset if there is one (status PENDING)
-    DcmDataset *rspDataset = NULL;
-    // Check if dataset is announced correctly
-    if (rsp.msg.CMoveRSP.DataSetType != DIMSE_DATASET_NULL) // Some of the sub operations have failed, thus a dataset with a list of them is attached
+    return cond;
+}
+
+/* ************************************************************************* */
+/*                            C-MOVE functionality                           */
+/* ************************************************************************* */
+
+// Sends a C-MOVE Request on given presentation context
+OFCondition DcmSCU::sendMOVERequest(const T_ASC_PresentationContextID presID,
+                                    const OFString& moveDestinationAETitle,
+                                    DcmDataset* dataset,
+                                    OFList<RetrieveResponse*>* responses)
+{
+    // Do some basic validity checks
+    if (!isConnected())
+        return DIMSE_ILLEGALASSOCIATION;
+    if (dataset == NULL)
+        return DIMSE_NULLKEY;
+
+    /* Prepare DIMSE data structures for issuing request */
+    OFCondition cond;
+    OFString tempStr;
+    T_ASC_PresentationContextID pcid = presID;
+    T_DIMSE_Message msg;
+    // make sure everything is zeroed (especially options)
+    bzero((char*)&msg, sizeof(msg));
+    DcmDataset* statusDetail = NULL;
+    T_DIMSE_C_MoveRQ* req    = &(msg.msg.CMoveRQ);
+    // Set type of message
+    msg.CommandField = DIMSE_C_MOVE_RQ;
+    // Set message ID
+    req->MessageID = nextMessageID();
+    // Announce dataset
+    req->DataSetType = DIMSE_DATASET_PRESENT;
+    // Set target for embedded C-Store's
+    OFStandard::strlcpy(req->MoveDestination, moveDestinationAETitle.c_str(), sizeof(req->MoveDestination));
+    // Set priority (mandatory)
+    req->Priority = DIMSE_PRIORITY_MEDIUM;
+
+    /* Determine SOP Class from presentation context */
+    OFString abstractSyntax, transferSyntax;
+    findPresentationContext(pcid, abstractSyntax, transferSyntax);
+    if (abstractSyntax.empty() || transferSyntax.empty())
+        return DIMSE_NOVALIDPRESENTATIONCONTEXTID;
+    OFStandard::strlcpy(req->AffectedSOPClassUID, abstractSyntax.c_str(), sizeof(req->AffectedSOPClassUID));
+
+    /* Send request */
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
     {
-      // Receive dataset
-      cond = receiveDIMSEDataset(&pcid, &rspDataset);
-      if (cond.bad())
-      {
-        DCMNET_ERROR("Unable to receive C-MOVE dataset on presentation context "
-          << OFstatic_cast(unsigned int, pcid) << ": " << DimseCondition::dump(tempStr, cond));
-        break;
-      }
-      moveRSP->m_dataset = rspDataset;
+        DCMNET_INFO("Sending C-MOVE Request");
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, msg, DIMSE_OUTGOING, dataset, pcid));
     }
-
-    // Handle C-MOVE response (has to handle all possible status flags)
-    cond = handleMOVEResponse(pcid, moveRSP.get(), waitForNextResponse);
+    else
+    {
+        DCMNET_INFO("Sending C-MOVE Request (MsgID " << req->MessageID << ")");
+    }
+    cond = sendDIMSEMessage(pcid, &msg, dataset);
     if (cond.bad())
     {
-      DCMNET_WARN("Unable to handle C-MOVE response correctly: " << cond.text() << " (ignored)");
-      // don't return here but trust the "waitForNextResponse" variable
+        DCMNET_ERROR("Failed sending C-MOVE request: " << DimseCondition::dump(tempStr, cond));
+        return cond;
     }
-    // if response could be handled successfully, add it to response list
-    else
+
+    /* Receive and handle C-MOVE response messages */
+    OFBool waitForNextResponse = OFTrue;
+    while (waitForNextResponse)
     {
-      if (responses != NULL) // only add if desired by caller
-        responses->push_back(moveRSP.release());
+        T_DIMSE_Message rsp;
+        // Make sure everything is zeroed, especially options
+        bzero((char*)&rsp, sizeof(rsp));
+        statusDetail = NULL;
+
+        // Receive command set
+        cond = receiveDIMSECommand(&pcid, &rsp, &statusDetail, NULL /* not interested in the command set */);
+        if (cond.bad())
+        {
+            DCMNET_ERROR("Failed receiving DIMSE response: " << DimseCondition::dump(tempStr, cond));
+            delete statusDetail;
+            break;
+        }
+
+        if (rsp.CommandField == DIMSE_C_MOVE_RSP)
+        {
+            if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+            {
+                DCMNET_INFO("Received C-MOVE Response");
+                DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
+            }
+            else
+            {
+                DCMNET_INFO("Received C-MOVE Response (" << DU_cmoveStatusString(rsp.msg.CMoveRSP.DimseStatus) << ")");
+            }
+        }
+        else
+        {
+            DCMNET_ERROR("Expected C-MOVE response but received DIMSE command 0x"
+                         << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
+                         << OFstatic_cast(unsigned int, rsp.CommandField));
+            DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
+            delete statusDetail;
+            cond = DIMSE_BADCOMMANDTYPE;
+            break;
+        }
+
+        // Prepare response package for response handler
+        OFunique_ptr<RetrieveResponse> moveRSP(new RetrieveResponse);
+        moveRSP->m_affectedSOPClassUID     = rsp.msg.CMoveRSP.AffectedSOPClassUID;
+        moveRSP->m_messageIDRespondedTo    = rsp.msg.CMoveRSP.MessageIDBeingRespondedTo;
+        moveRSP->m_status                  = rsp.msg.CMoveRSP.DimseStatus;
+        moveRSP->m_numberOfRemainingSubops = rsp.msg.CMoveRSP.NumberOfRemainingSubOperations;
+        moveRSP->m_numberOfCompletedSubops = rsp.msg.CMoveRSP.NumberOfCompletedSubOperations;
+        moveRSP->m_numberOfFailedSubops    = rsp.msg.CMoveRSP.NumberOfFailedSubOperations;
+        moveRSP->m_numberOfWarningSubops   = rsp.msg.CMoveRSP.NumberOfWarningSubOperations;
+        moveRSP->m_statusDetail            = statusDetail;
+        // DCMNET_DEBUG("C-MOVE response has status 0x"
+        //  << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
+        //  << moveRSP->m_status);
+        if (statusDetail != NULL)
+        {
+            DCMNET_DEBUG("Response has status detail:" << OFendl << DcmObject::PrintHelper(*statusDetail));
+        }
+
+        // Receive dataset if there is one (status PENDING)
+        DcmDataset* rspDataset = NULL;
+        // Check if dataset is announced correctly
+        if (rsp.msg.CMoveRSP.DataSetType != DIMSE_DATASET_NULL) // Some of the sub operations have failed, thus a
+                                                                // dataset with a list of them is attached
+        {
+            // Receive dataset
+            cond = receiveDIMSEDataset(&pcid, &rspDataset);
+            if (cond.bad())
+            {
+                DCMNET_ERROR("Unable to receive C-MOVE dataset on presentation context "
+                             << OFstatic_cast(unsigned int, pcid) << ": " << DimseCondition::dump(tempStr, cond));
+                break;
+            }
+            moveRSP->m_dataset = rspDataset;
+        }
+
+        // Handle C-MOVE response (has to handle all possible status flags)
+        cond = handleMOVEResponse(pcid, moveRSP.get(), waitForNextResponse);
+        if (cond.bad())
+        {
+            DCMNET_WARN("Unable to handle C-MOVE response correctly: " << cond.text() << " (ignored)");
+            // don't return here but trust the "waitForNextResponse" variable
+        }
+        // if response could be handled successfully, add it to response list
+        else
+        {
+            if (responses != NULL) // only add if desired by caller
+                responses->push_back(moveRSP.release());
+        }
     }
-  }
-  /* All responses received or break signal occurred */
-  return cond;
+    /* All responses received or break signal occurred */
+    return cond;
 }
 
-
 // Standard handler for C-MOVE message responses
-OFCondition DcmSCU::handleMOVEResponse( const T_ASC_PresentationContextID /* presID */,
-                                        RetrieveResponse *response,
-                                        OFBool &waitForNextResponse )
-{
-  // Do some basic validity checks
-  if (!isConnected())
-    return DIMSE_ILLEGALASSOCIATION;
-  if (response == NULL)
-    return DIMSE_NULLKEY;
-
-  DCMNET_DEBUG("Handling C-MOVE Response");
-  switch (response->m_status) {
-  case STATUS_MOVE_Failed_IdentifierDoesNotMatchSOPClass:
-    waitForNextResponse = OFFalse;
-    DCMNET_ERROR("Identifier does not match SOP class in C-MOVE response");
-    break;
-  case STATUS_MOVE_Failed_MoveDestinationUnknown:
-    waitForNextResponse = OFFalse;
-    DCMNET_ERROR("Move destination unknown");
-    break;
-  case STATUS_MOVE_Failed_UnableToProcess:
-    waitForNextResponse = OFFalse;
-    DCMNET_ERROR("Unable to process C-Move response");
-    break;
-  case STATUS_MOVE_Cancel_SubOperationsTerminatedDueToCancelIndication:
-    waitForNextResponse = OFFalse;
-    DCMNET_DEBUG("Suboperations canceled by server due to CANCEL indication");
-    break;
-  case STATUS_MOVE_Warning_SubOperationsCompleteOneOrMoreFailures:
-    waitForNextResponse = OFFalse;
-    DCMNET_WARN("Suboperations of C-MOVE completed with one or more failures");
-    break;
-  case STATUS_Pending:
-    /* in this case the current C-MOVE-RSP indicates that */
-    /* there will be some more results */
-    waitForNextResponse = OFTrue;
-    DCMNET_DEBUG("One or more pending C-MOVE responses");
-    break;
-  case STATUS_Success:
-    /* in this case, we received the last C-MOVE-RSP so there */
-    /* will be no other responses we have to wait for. */
-    waitForNextResponse = OFFalse;
-    DCMNET_DEBUG("Received final C-MOVE response, no more C-MOVE responses expected");
-    break;
-  default:
-    /* in all other cases, don't expect further responses to come */
+OFCondition DcmSCU::handleMOVEResponse(const T_ASC_PresentationContextID /* presID */,
+                                       RetrieveResponse* response,
+                                       OFBool& waitForNextResponse)
+{
     waitForNextResponse = OFFalse;
-    DCMNET_WARN("Status is 0x"
-      << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
-      << response->m_status << " (unknown)");
-    DCMNET_WARN("Will not wait for further C-MOVE responses");
-    break;
-  } //switch
+    if (response == NULL)
+        return DIMSE_NULLKEY;
 
-  return EC_Normal;
+    DCMNET_DEBUG("Handling C-MOVE Response");
+    OFString s;
+    s = DU_cmoveStatusString(response->m_status);
+    return handleSessionResponseDefault(response->m_status, s, waitForNextResponse);
 }
 
-
 /* ************************************************************************* */
 /*               C-GET and accompanying C-STORE functionality                */
 /* ************************************************************************* */
 
 // Sends a C-GET Request on given presentation context
 OFCondition DcmSCU::sendCGETRequest(const T_ASC_PresentationContextID presID,
-                                    DcmDataset *dataset,
-                                    OFList<RetrieveResponse*> *responses)
-{
-  // Do some basic validity checks
-  if (!isConnected())
-    return DIMSE_ILLEGALASSOCIATION;
-  if (dataset == NULL)
-    return DIMSE_NULLKEY;
-
-  /* Prepare DIMSE data structures for issuing request */
-  OFCondition cond;
-  OFString tempStr;
-  T_ASC_PresentationContextID pcid = presID;
-  T_DIMSE_Message msg;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&msg, sizeof(msg));
-  T_DIMSE_C_GetRQ* req = &(msg.msg.CGetRQ);
-  // Set type of message
-  msg.CommandField = DIMSE_C_GET_RQ;
-  // Set message ID
-  req->MessageID = nextMessageID();
-  // Announce dataset
-  req->DataSetType = DIMSE_DATASET_PRESENT;
-  // Specify priority
-  req->Priority = DIMSE_PRIORITY_MEDIUM;
-
-  // Determine SOP Class from presentation context
-  OFString abstractSyntax, transferSyntax;
-  findPresentationContext(pcid, abstractSyntax, transferSyntax);
-  if (abstractSyntax.empty() || transferSyntax.empty())
-    return DIMSE_NOVALIDPRESENTATIONCONTEXTID;
-  OFStandard::strlcpy(req->AffectedSOPClassUID, abstractSyntax.c_str(), sizeof(req->AffectedSOPClassUID));
-
-  /* Send request */
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-  {
-    DCMNET_INFO("Sending C-GET Request");
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, msg, DIMSE_OUTGOING, dataset, pcid));
-  } else {
-    DCMNET_INFO("Sending C-GET Request (MsgID " << req->MessageID << ")");
-  }
-  cond = sendDIMSEMessage(pcid, &msg, dataset);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed sending C-GET request: " << DimseCondition::dump(tempStr, cond));
-    return cond;
-  }
+                                    DcmDataset* dataset,
+                                    OFList<RetrieveResponse*>* responses)
+{
+    // Do some basic validity checks
+    if (!isConnected())
+        return DIMSE_ILLEGALASSOCIATION;
+    if (dataset == NULL)
+        return DIMSE_NULLKEY;
 
-  cond = handleCGETSession(pcid, dataset, responses);
-  return cond;
-}
+    /* Prepare DIMSE data structures for issuing request */
+    OFCondition cond;
+    OFString tempStr;
+    T_ASC_PresentationContextID pcid = presID;
+    T_DIMSE_Message msg;
+    // Make sure everything is zeroed (especially options)
+    bzero((char*)&msg, sizeof(msg));
+    T_DIMSE_C_GetRQ* req = &(msg.msg.CGetRQ);
+    // Set type of message
+    msg.CommandField = DIMSE_C_GET_RQ;
+    // Set message ID
+    req->MessageID = nextMessageID();
+    // Announce dataset
+    req->DataSetType = DIMSE_DATASET_PRESENT;
+    // Specify priority
+    req->Priority = DIMSE_PRIORITY_MEDIUM;
+
+    // Determine SOP Class from presentation context
+    OFString abstractSyntax, transferSyntax;
+    findPresentationContext(pcid, abstractSyntax, transferSyntax);
+    if (abstractSyntax.empty() || transferSyntax.empty())
+        return DIMSE_NOVALIDPRESENTATIONCONTEXTID;
+    OFStandard::strlcpy(req->AffectedSOPClassUID, abstractSyntax.c_str(), sizeof(req->AffectedSOPClassUID));
+
+    /* Send request */
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+    {
+        DCMNET_INFO("Sending C-GET Request");
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, msg, DIMSE_OUTGOING, dataset, pcid));
+    }
+    else
+    {
+        DCMNET_INFO("Sending C-GET Request (MsgID " << req->MessageID << ")");
+    }
+    cond = sendDIMSEMessage(pcid, &msg, dataset);
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Failed sending C-GET request: " << DimseCondition::dump(tempStr, cond));
+        return cond;
+    }
 
+    cond = handleCGETSession(pcid, dataset, responses);
+    return cond;
+}
 
 // Does the logic for switching between C-GET Response and C-STORE Requests
 OFCondition DcmSCU::handleCGETSession(const T_ASC_PresentationContextID /* presID */,
-                                      DcmDataset * /* dataset */,
-                                      OFList<RetrieveResponse*> *responses)
+                                      DcmDataset* /* dataset */,
+                                      OFList<RetrieveResponse*>responses)
 {
-  OFCondition result;
-  OFBool continueSession = OFTrue;
-  OFString tempStr;
+    OFCondition result;
+    OFBool continueSession = OFTrue;
+    OFString tempStr;
 
-  // As long we want to continue (usually, as long as we receive more objects,
-  // i.e. the final C-GET response has not arrived yet)
-  while (continueSession)
-  {
-    T_DIMSE_Message rsp;
-    // Make sure everything is zeroed (especially options)
-    bzero((char*)&rsp, sizeof(rsp));
+    // As long we want to continue (usually, as long as we receive more objects,
+    // i.e. the final C-GET response has not arrived yet)
+    while (continueSession)
+    {
+        T_DIMSE_Message rsp;
+        // Make sure everything is zeroed (especially options)
+        bzero((char*)&rsp, sizeof(rsp));
 
-    DcmDataset *statusDetail = NULL;
-    T_ASC_PresentationContextID pcid = 0;
+        DcmDataset* statusDetail         = NULL;
+        T_ASC_PresentationContextID pcid = 0;
 
-    // Receive command set
-    result = receiveDIMSECommand(&pcid, &rsp, &statusDetail, NULL /* not interested in the command set */);
-    if (result.bad())
-    {
-      DCMNET_ERROR("Failed receiving DIMSE command: " << DimseCondition::dump(tempStr, result));
-      delete statusDetail;
-      break;
-    }
-    // Handle C-GET Response
-    if (rsp.CommandField == DIMSE_C_GET_RSP)
-    {
-      if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-      {
-        DCMNET_INFO("Received C-GET Response");
-        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
-      } else {
-        DCMNET_INFO("Received C-GET Response (" << DU_cgetStatusString(rsp.msg.CGetRSP.DimseStatus) << ")");
-      }
-      // Prepare response package for response handler
-      OFunique_ptr<RetrieveResponse> getRSP(new RetrieveResponse());
-      getRSP->m_affectedSOPClassUID = rsp.msg.CGetRSP.AffectedSOPClassUID;
-      getRSP->m_messageIDRespondedTo = rsp.msg.CGetRSP.MessageIDBeingRespondedTo;
-      getRSP->m_status = rsp.msg.CGetRSP.DimseStatus;
-      getRSP->m_numberOfRemainingSubops = rsp.msg.CGetRSP.NumberOfRemainingSubOperations;
-      getRSP->m_numberOfCompletedSubops = rsp.msg.CGetRSP.NumberOfCompletedSubOperations;
-      getRSP->m_numberOfFailedSubops = rsp.msg.CGetRSP.NumberOfFailedSubOperations;
-      getRSP->m_numberOfWarningSubops = rsp.msg.CGetRSP.NumberOfWarningSubOperations;
-      getRSP->m_statusDetail = statusDetail;
-      if (statusDetail != NULL)
-      {
-        DCMNET_DEBUG("Response has status detail:" << OFendl << DcmObject::PrintHelper(*statusDetail));
-        statusDetail = NULL; // forget reference to status detail, will be deleted with getRSP
-      }
-      result = handleCGETResponse(pcid, getRSP.get(), continueSession);
-      if (result.bad())
-      {
-        DCMNET_WARN("Unable to handle C-GET response correctly: " << result.text() << " (ignored)");
-        // don't return here but trust the "continueSession" variable
-      }
-      // if response could be handled successfully, add it to response list
-      else {
-        if (responses != NULL) // only add if desired by caller
-          responses->push_back(getRSP.release());
-      }
-    }
-
-    // Handle C-STORE Request
-    else if (rsp.CommandField == DIMSE_C_STORE_RQ)
-    {
-      if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-      {
-        DCMNET_INFO("Received C-STORE Request");
-        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
-      } else {
-        DCMNET_INFO("Received C-STORE Request (MsgID " << rsp.msg.CStoreRQ.MessageID << ")");
-      }
-      // Receive dataset if there is one (status PENDING)
-      DcmDataset *rspDataset = NULL;
-      // Check if dataset is announced correctly
-      if (rsp.msg.CStoreRQ.DataSetType == DIMSE_DATASET_NULL)
-      {
-        DCMNET_WARN("Incoming C-STORE with no dataset, trying to receive one anyway");
-      }
-      Uint16 desiredCStoreReturnStatus = 0;
-      // handle normal storage mode, i.e. receive in memory and store to disk
-      if (m_storageMode == DCMSCU_STORAGE_DISK)
-      {
-        // Receive dataset
-        result = receiveDIMSEDataset(&pcid, &rspDataset);
+        // Receive command set
+        result = receiveDIMSECommand(&pcid, &rsp, &statusDetail, NULL /* not interested in the command set */);
         if (result.bad())
         {
-          result = DIMSE_NULLKEY;
-          desiredCStoreReturnStatus = STATUS_STORE_Error_CannotUnderstand;
-        } else {
-          result = handleSTORERequest(pcid, rspDataset, continueSession, desiredCStoreReturnStatus);
+            DCMNET_ERROR("Failed receiving DIMSE command: " << DimseCondition::dump(tempStr, result));
+            delete statusDetail;
+            break;
         }
-      }
-      // handle bit preserving storage mode, i.e. receive directly to disk
-      else if (m_storageMode == DCMSCU_STORAGE_BIT_PRESERVING)
-      {
-        OFString storageFilename;
-        OFStandard::combineDirAndFilename(storageFilename, m_storageDir, rsp.msg.CStoreRQ.AffectedSOPInstanceUID, OFTrue);
-        result = handleSTORERequestFile(&pcid, storageFilename, &(rsp.msg.CStoreRQ));
-        if (result.good())
+        // Handle C-GET Response
+        if (rsp.CommandField == DIMSE_C_GET_RSP)
         {
-          notifyInstanceStored(storageFilename, rsp.msg.CStoreRQ.AffectedSOPClassUID, rsp.msg.CStoreRQ.AffectedSOPInstanceUID);
+            if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+            {
+                DCMNET_INFO("Received C-GET Response");
+                DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
+            }
+            else
+            {
+                DCMNET_INFO("Received C-GET Response (" << DU_cgetStatusString(rsp.msg.CGetRSP.DimseStatus) << ")");
+            }
+            // Prepare response package for response handler
+            OFunique_ptr<RetrieveResponse> getRSP(new RetrieveResponse());
+            getRSP->m_affectedSOPClassUID     = rsp.msg.CGetRSP.AffectedSOPClassUID;
+            getRSP->m_messageIDRespondedTo    = rsp.msg.CGetRSP.MessageIDBeingRespondedTo;
+            getRSP->m_status                  = rsp.msg.CGetRSP.DimseStatus;
+            getRSP->m_numberOfRemainingSubops = rsp.msg.CGetRSP.NumberOfRemainingSubOperations;
+            getRSP->m_numberOfCompletedSubops = rsp.msg.CGetRSP.NumberOfCompletedSubOperations;
+            getRSP->m_numberOfFailedSubops    = rsp.msg.CGetRSP.NumberOfFailedSubOperations;
+            getRSP->m_numberOfWarningSubops   = rsp.msg.CGetRSP.NumberOfWarningSubOperations;
+            getRSP->m_statusDetail            = statusDetail;
+            if (statusDetail != NULL)
+            {
+                DCMNET_DEBUG("Response has status detail:" << OFendl << DcmObject::PrintHelper(*statusDetail));
+                statusDetail = NULL; // forget reference to status detail, will be deleted with getRSP
+            }
+            result = handleCGETResponse(pcid, getRSP.get(), continueSession);
+            if (result.bad())
+            {
+                DCMNET_WARN("Unable to handle C-GET response correctly: " << result.text() << " (ignored)");
+                // don't return here but trust the "continueSession" variable
+            }
+            // if response could be handled successfully, add it to response list
+            else
+            {
+                if (responses != NULL) // only add if desired by caller
+                    responses->push_back(getRSP.release());
+            }
         }
-      }
-      // handle ignore storage mode, i.e. ignore received dataset and do not store at all
-      else
-      {
-        result = ignoreSTORERequest(pcid, rsp.msg.CStoreRQ);
-      }
-
-      // Evaluate result from C-STORE request handling and send response
-      if (result.bad())
-      {
-        desiredCStoreReturnStatus = STATUS_STORE_Error_CannotUnderstand;
-        continueSession = OFFalse;
-      }
-      result = sendSTOREResponse(pcid, desiredCStoreReturnStatus, rsp.msg.CStoreRQ);
-      if (result.bad())
-      {
-        continueSession = OFFalse;
-      }
-    }
-
-    // Handle other DIMSE command (error since other command than GET/STORE not expected)
-    else
-    {
-      DCMNET_ERROR("Expected C-GET response or C-STORE request but received DIMSE command 0x"
-        << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
-        << OFstatic_cast(unsigned int, rsp.CommandField));
-      DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
-      result = DIMSE_BADCOMMANDTYPE;
-      continueSession = OFFalse;
-    }
 
-    delete statusDetail; // should be NULL if not existing or added to response list
-    statusDetail = NULL;
-  }
-  /* All responses received or break signal occurred */
+        // Handle C-STORE Request
+        else if (rsp.CommandField == DIMSE_C_STORE_RQ)
+        {
+            if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+            {
+                DCMNET_INFO("Received C-STORE Request");
+                DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
+            }
+            else
+            {
+                DCMNET_INFO("Received C-STORE Request (MsgID " << rsp.msg.CStoreRQ.MessageID << ")");
+            }
+            // Receive dataset if there is one (status PENDING)
+            DcmDataset* rspDataset = NULL;
+            // Check if dataset is announced correctly
+            if (rsp.msg.CStoreRQ.DataSetType == DIMSE_DATASET_NULL)
+            {
+                DCMNET_WARN("Incoming C-STORE with no dataset, trying to receive one anyway");
+            }
+            Uint16 desiredCStoreReturnStatus = 0;
+            // handle normal storage mode, i.e. receive in memory and store to disk
+            if (m_storageMode == DCMSCU_STORAGE_DISK)
+            {
+                // Receive dataset
+                result = receiveDIMSEDataset(&pcid, &rspDataset);
+                if (result.bad())
+                {
+                    result                    = DIMSE_NULLKEY;
+                    desiredCStoreReturnStatus = STATUS_STORE_Error_CannotUnderstand;
+                }
+                else
+                {
+                    result = handleSTORERequest(pcid, rspDataset, continueSession, desiredCStoreReturnStatus);
+                }
+            }
+            // handle bit preserving storage mode, i.e. receive directly to disk
+            else if (m_storageMode == DCMSCU_STORAGE_BIT_PRESERVING)
+            {
+                OFString storageFilename;
+                OFStandard::combineDirAndFilename(
+                    storageFilename, m_storageDir, rsp.msg.CStoreRQ.AffectedSOPInstanceUID, OFTrue);
+                result = handleSTORERequestFile(&pcid, storageFilename, &(rsp.msg.CStoreRQ));
+                if (result.good())
+                {
+                    notifyInstanceStored(
+                        storageFilename, rsp.msg.CStoreRQ.AffectedSOPClassUID, rsp.msg.CStoreRQ.AffectedSOPInstanceUID);
+                }
+            }
+            // handle ignore storage mode, i.e. ignore received dataset and do not store at all
+            else
+            {
+                result = ignoreSTORERequest(pcid, rsp.msg.CStoreRQ);
+            }
+
+            // Evaluate result from C-STORE request handling and send response
+            if (result.bad())
+            {
+                desiredCStoreReturnStatus = STATUS_STORE_Error_CannotUnderstand;
+                continueSession           = OFFalse;
+            }
+            result = sendSTOREResponse(pcid, desiredCStoreReturnStatus, rsp.msg.CStoreRQ);
+            if (result.bad())
+            {
+                continueSession = OFFalse;
+            }
+        }
 
-  return result;
+        // Handle other DIMSE command (error since other command than GET/STORE not expected)
+        else
+        {
+            DCMNET_ERROR("Expected C-GET response or C-STORE request but received DIMSE command 0x"
+                         << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
+                         << OFstatic_cast(unsigned int, rsp.CommandField));
+            DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
+            result          = DIMSE_BADCOMMANDTYPE;
+            continueSession = OFFalse;
+        }
 
-}
+        delete statusDetail; // should be NULL if not existing or added to response list
+        statusDetail = NULL;
+    }
+    /* All responses received or break signal occurred */
 
+    return result;
+}
 
 // Handles single C-GET Response
 OFCondition DcmSCU::handleCGETResponse(const T_ASC_PresentationContextID /* presID */,
                                        RetrieveResponse* response,
                                        OFBool& continueCGETSession)
 {
-  // Do some basic validity checks
-  if (!isConnected())
-    return DIMSE_ILLEGALASSOCIATION;
-  if (response == NULL)
-    return DIMSE_NULLKEY;
-
-  DCMNET_DEBUG("Handling C-GET Response");
-
-  /* First, perform separate check for 0xCxxx error codes */
-  Uint16 highNibble = response->m_status & 0xf000;
-  if (highNibble == STATUS_GET_Failed_UnableToProcess)
-  {
-    continueCGETSession = OFFalse;
-    DCMNET_ERROR("Unable to Process");
-    DCMNET_WARN("Full status is 0x"
-      << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
-      << response->m_status);
-    return EC_Normal;
-  }
-
-  /* Check for other error codes */
-  switch (response->m_status) {
-  case STATUS_GET_Refused_OutOfResourcesNumberOfMatches:
-    continueCGETSession = OFFalse;
-    DCMNET_ERROR("Out of Resources - Unable to calculate number of matches");
-    break;
-  case STATUS_GET_Refused_OutOfResourcesSubOperations:
-    continueCGETSession = OFFalse;
-    DCMNET_ERROR("Out of Resources - Unable to perform sub-operations");
-    break;
-  case STATUS_GET_Failed_IdentifierDoesNotMatchSOPClass:
     continueCGETSession = OFFalse;
-    DCMNET_ERROR("Identifier does not match SOP class");
-    break;
-  case STATUS_GET_Cancel_SubOperationsTerminatedDueToCancelIndication:
-    continueCGETSession = OFFalse;
-    DCMNET_DEBUG("Suboperations canceled by server due to CANCEL indication");
-    break;
-  case STATUS_GET_Warning_SubOperationsCompleteOneOrMoreFailures:
-    continueCGETSession = OFFalse;
-    DCMNET_WARN("Suboperations of C-GET completed with one or more failures");
-    break;
-  case STATUS_Pending:
-    /* in this case the current C-MOVE-RSP indicates that */
-    /* there will be some more results */
-    continueCGETSession = OFTrue;
-    DCMNET_DEBUG("One or more pending C-GET responses");
-    break;
-  case STATUS_Success:
-    /* in this case, we received the last C-MOVE-RSP so there */
-    /* will be no other responses we have to wait for. */
-    continueCGETSession = OFFalse;
-    DCMNET_DEBUG("Received final C-GET response, no more C-GET responses expected");
-    break;
-  default:
-    /* in all other cases, don't expect further responses to come */
-    continueCGETSession = OFFalse;
-    DCMNET_WARN("Status is 0x"
-      << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
-      << response->m_status << " (unknown)");
-    DCMNET_WARN("Will not wait for further C-GET responses");
-    break;
-  } //switch
+    if (response == NULL)
+        return DIMSE_NULLKEY;
 
-  return EC_Normal;
+    DCMNET_DEBUG("Handling C-GET Response");
+    OFString s;
+    s = DU_cgetStatusString(response->m_status);
+    return handleSessionResponseDefault(response->m_status, s, continueCGETSession);
 }
 
-
 // Handles single C-STORE Request received during C-GET session
 OFCondition DcmSCU::handleSTORERequest(const T_ASC_PresentationContextID /* presID */,
-                                       DcmDataset *incomingObject,
+                                       DcmDatasetincomingObject,
                                        OFBool& /* continueCGETSession */,
                                        Uint16& cStoreReturnStatus)
 {
-  if (incomingObject == NULL)
-    return DIMSE_NULLKEY;
+    if (incomingObject == NULL)
+        return DIMSE_NULLKEY;
 
-  OFString sopClassUID;
-  OFString sopInstanceUID;
-  OFCondition result = incomingObject->findAndGetOFString(DCM_SOPClassUID, sopClassUID);
-  if (result.good())
-    result = incomingObject->findAndGetOFString(DCM_SOPInstanceUID, sopInstanceUID);
-  if (result.bad())
-  {
-    DCMNET_ERROR("Cannot store received object: either SOP Instance or SOP Class UID not present");
-    cStoreReturnStatus = STATUS_STORE_Error_DataSetDoesNotMatchSOPClass;
-    delete incomingObject;
-    return EC_TagNotFound;
-  }
+    OFString sopClassUID;
+    OFString sopInstanceUID;
+    OFCondition result = incomingObject->findAndGetOFString(DCM_SOPClassUID, sopClassUID);
+    if (result.good())
+        result = incomingObject->findAndGetOFString(DCM_SOPInstanceUID, sopInstanceUID);
+    if (result.bad())
+    {
+        DCMNET_ERROR("Cannot store received object: either SOP Instance or SOP Class UID not present");
+        cStoreReturnStatus = STATUS_STORE_Error_DataSetDoesNotMatchSOPClass;
+        delete incomingObject;
+        return EC_TagNotFound;
+    }
 
-  OFString filename = createStorageFilename(incomingObject);
-  if (OFStandard::fileExists(filename))
-  {
-    DCMNET_WARN("DICOM file already exists, overwriting: " << filename);
-  }
-  DcmFileFormat dcmff(incomingObject, OFFalse /* do not copy but take ownership */);
-  result = dcmff.saveFile(filename);
-  if (result.good())
-  {
-    E_TransferSyntax xferSyntax;
-    getDatasetInfo(incomingObject, sopClassUID, sopInstanceUID, xferSyntax);
-    notifyInstanceStored(filename, sopClassUID, sopInstanceUID);
-    cStoreReturnStatus = STATUS_Success;
-  }
-  else
-  {
-    DCMNET_ERROR("cannot write DICOM file: " << filename);
-    cStoreReturnStatus = STATUS_STORE_Refused_OutOfResources;
+    OFString filename = createStorageFilename(incomingObject);
+    if (OFStandard::fileExists(filename))
+    {
+        DCMNET_WARN("DICOM file already exists, overwriting: " << filename);
+    }
+    DcmFileFormat dcmff(incomingObject, OFFalse /* do not copy but take ownership */);
+    result = dcmff.saveFile(filename);
+    if (result.good())
+    {
+        E_TransferSyntax xferSyntax;
+        getDatasetInfo(incomingObject, sopClassUID, sopInstanceUID, xferSyntax);
+        notifyInstanceStored(filename, sopClassUID, sopInstanceUID);
+        cStoreReturnStatus = STATUS_Success;
+    }
+    else
+    {
+        DCMNET_ERROR("cannot write DICOM file: " << filename);
+        cStoreReturnStatus = STATUS_STORE_Refused_OutOfResources;
 
-    // delete incomplete file
-    OFStandard::deleteFile(filename);
-  }
+        // delete incomplete file
+        OFStandard::deleteFile(filename);
+    }
 
-  return result;
+    return result;
 }
 
-OFCondition DcmSCU::handleSTORERequestFile(T_ASC_PresentationContextID *presID,
-                                           const OFString &filename,
-                                           T_DIMSE_C_StoreRQ *request)
+OFCondition DcmSCU::handleSTORERequestFile(T_ASC_PresentationContextIDpresID,
+                                           const OFStringfilename,
+                                           T_DIMSE_C_StoreRQrequest)
 {
-  if (filename.empty())
-    return EC_IllegalParameter;
+    if (filename.empty())
+        return EC_IllegalParameter;
 
-  /* in the following, we want to receive data over the network and write it to a file */
-  /* exactly the way it was received over the network. Hence, a filestream will be created and the data */
-  /* set will be received and written to the file through the call to DIMSE_receiveDataSetInFile(...).*/
-  /* create filestream */
-  DcmOutputFileStream *filestream = NULL;
-  OFCondition cond = DIMSE_createFilestream(filename, request, m_assoc, *presID, OFTrue, &filestream);
-  if (cond.good())
-  {
-    if (m_progressNotificationMode)
+    /* in the following, we want to receive data over the network and write it to a file */
+    /* exactly the way it was received over the network. Hence, a filestream will be created and the data */
+    /* set will be received and written to the file through the call to DIMSE_receiveDataSetInFile(...).*/
+    /* create filestream */
+    DcmOutputFileStream* filestream = NULL;
+    OFCondition cond                = DIMSE_createFilestream(filename, request, m_assoc, *presID, OFTrue, &filestream);
+    if (cond.good())
     {
-      cond = DIMSE_receiveDataSetInFile(m_assoc, m_blockMode, m_dimseTimeout, presID, filestream,
-                                        callbackRECEIVEProgress, this /*callbackData*/);
-    } else {
-      cond = DIMSE_receiveDataSetInFile(m_assoc, m_blockMode, m_dimseTimeout, presID, filestream,
-                                        NULL /*callback*/, NULL /*callbackData*/);
+        if (m_progressNotificationMode)
+        {
+            cond = DIMSE_receiveDataSetInFile(m_assoc,
+                                              m_blockMode,
+                                              m_dimseTimeout,
+                                              presID,
+                                              filestream,
+                                              callbackRECEIVEProgress,
+                                              this /*callbackData*/);
+        }
+        else
+        {
+            cond = DIMSE_receiveDataSetInFile(
+                m_assoc, m_blockMode, m_dimseTimeout, presID, filestream, NULL /*callback*/, NULL /*callbackData*/);
+        }
+        delete filestream;
+        if (cond != EC_Normal)
+        {
+            OFStandard::deleteFile(filename);
+        }
+        DCMNET_DEBUG("Received dataset on presentation context " << OFstatic_cast(unsigned int, *presID));
     }
-    delete filestream;
-    if (cond != EC_Normal)
+    else
     {
-      OFStandard::deleteFile(filename);
+        OFString tempStr;
+        DCMNET_ERROR("Unable to receive and store dataset on presentation context "
+                     << OFstatic_cast(unsigned int, *presID) << ": " << DimseCondition::dump(tempStr, cond));
     }
-    DCMNET_DEBUG("Received dataset on presentation context " << OFstatic_cast(unsigned int, *presID));
-  }
-  else
-  {
-    OFString tempStr;
-    DCMNET_ERROR("Unable to receive and store dataset on presentation context "
-      << OFstatic_cast(unsigned int, *presID) << ": " << DimseCondition::dump(tempStr, cond));
-  }
-  return cond;
-}
-
-
-OFCondition DcmSCU::sendSTOREResponse(T_ASC_PresentationContextID presID,
-                                      Uint16 status,
-                                      const T_DIMSE_C_StoreRQ& request)
-{
-  // Send back response
-  T_DIMSE_Message response;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&response, sizeof(response));
-  T_DIMSE_C_StoreRSP &storeRsp = response.msg.CStoreRSP;
-  response.CommandField = DIMSE_C_STORE_RSP;
-  storeRsp.MessageIDBeingRespondedTo = request.MessageID;
-  storeRsp.DimseStatus = status;
-  storeRsp.DataSetType = DIMSE_DATASET_NULL;
-  /* Following information is optional and normally not sent by the underlying
-   * dcmnet routines. However, maybe this could be changed later, so insert it.
-   */
-  OFStandard::strlcpy(storeRsp.AffectedSOPClassUID, request.AffectedSOPClassUID, sizeof(storeRsp.AffectedSOPClassUID));
-  OFStandard::strlcpy(storeRsp.AffectedSOPInstanceUID, request.AffectedSOPInstanceUID, sizeof(storeRsp.AffectedSOPInstanceUID));
-  storeRsp.opts = O_STORE_AFFECTEDSOPCLASSUID | O_STORE_AFFECTEDSOPINSTANCEUID;
-
-  OFString tempStr;
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-  {
-    DCMNET_INFO("Sending C-STORE Response");
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_OUTGOING, NULL, presID));
-  } else {
-    DCMNET_INFO("Sending C-STORE Response (" << DU_cstoreStatusString(status) << ")");
-  }
-  OFCondition cond = sendDIMSEMessage(presID, &response, NULL /*dataObject*/);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed sending C-STORE response: " << DimseCondition::dump(tempStr, cond));
-  }
-  return cond;
+    return cond;
 }
 
-
-OFString DcmSCU::createStorageFilename(DcmDataset *dataset)
+OFCondition
+DcmSCU::sendSTOREResponse(T_ASC_PresentationContextID presID, Uint16 status, const T_DIMSE_C_StoreRQ& request)
 {
-  OFString sopClassUID, sopInstanceUID;
-  E_TransferSyntax dummy;
-  getDatasetInfo(dataset, sopClassUID, sopInstanceUID, dummy);
-  // Create unique filename
-  if (sopClassUID.empty() || sopInstanceUID.empty())
-    return "";
-  OFString name = dcmSOPClassUIDToModality(sopClassUID.c_str(), "UNKNOWN");
-  name += ".";
-  name += sopInstanceUID;
-  OFString returnStr;
-  OFStandard::combineDirAndFilename(returnStr, m_storageDir, name, OFTrue);
-  return returnStr;
+    // Send back response
+    T_DIMSE_Message response;
+    // Make sure everything is zeroed (especially options)
+    bzero((char*)&response, sizeof(response));
+    T_DIMSE_C_StoreRSP& storeRsp       = response.msg.CStoreRSP;
+    response.CommandField              = DIMSE_C_STORE_RSP;
+    storeRsp.MessageIDBeingRespondedTo = request.MessageID;
+    storeRsp.DimseStatus               = status;
+    storeRsp.DataSetType               = DIMSE_DATASET_NULL;
+    /* Following information is optional and normally not sent by the underlying
+     * dcmnet routines. However, maybe this could be changed later, so insert it.
+     */
+    OFStandard::strlcpy(
+        storeRsp.AffectedSOPClassUID, request.AffectedSOPClassUID, sizeof(storeRsp.AffectedSOPClassUID));
+    OFStandard::strlcpy(
+        storeRsp.AffectedSOPInstanceUID, request.AffectedSOPInstanceUID, sizeof(storeRsp.AffectedSOPInstanceUID));
+    storeRsp.opts = O_STORE_AFFECTEDSOPCLASSUID | O_STORE_AFFECTEDSOPINSTANCEUID;
+
+    OFString tempStr;
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+    {
+        DCMNET_INFO("Sending C-STORE Response");
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_OUTGOING, NULL, presID));
+    }
+    else
+    {
+        DCMNET_INFO("Sending C-STORE Response (" << DU_cstoreStatusString(status) << ")");
+    }
+    OFCondition cond = sendDIMSEMessage(presID, &response, NULL /*dataObject*/);
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Failed sending C-STORE response: " << DimseCondition::dump(tempStr, cond));
+    }
+    return cond;
 }
 
+OFString DcmSCU::createStorageFilename(DcmDataset* dataset)
+{
+    OFString sopClassUID, sopInstanceUID;
+    E_TransferSyntax dummy;
+    getDatasetInfo(dataset, sopClassUID, sopInstanceUID, dummy);
+    // Create unique filename
+    if (sopClassUID.empty() || sopInstanceUID.empty())
+        return "";
+    OFString name = dcmSOPClassUIDToModality(sopClassUID.c_str(), "UNKNOWN");
+    name += ".";
+    name += sopInstanceUID;
+    OFString returnStr;
+    OFStandard::combineDirAndFilename(returnStr, m_storageDir, name, OFTrue);
+    return returnStr;
+}
 
-OFCondition DcmSCU::ignoreSTORERequest(T_ASC_PresentationContextID presID,
-                                       const T_DIMSE_C_StoreRQ &request)
+OFCondition DcmSCU::ignoreSTORERequest(T_ASC_PresentationContextID presID, const T_DIMSE_C_StoreRQ& request)
 {
 
-  /* We cannot create the filestream, so ignore the incoming dataset and return an out-of-resources error to the SCU */
-  DIC_UL bytesRead = 0;
-  DIC_UL pdvCount=0;
-  DCMNET_DEBUG("Ignoring incoming C-STORE dataset on presentation context "
-    << OFstatic_cast(unsigned int, presID)
-    << " with Affected SOP Instance UID: " << request.AffectedSOPInstanceUID );
-  OFCondition result = DIMSE_ignoreDataSet(m_assoc, m_blockMode, m_dimseTimeout, &bytesRead, &pdvCount);
-  if (result.good())
-  {
-    DCMNET_TRACE("Successfully skipped " << bytesRead << " bytes in " << pdvCount << " PDVs");
-  }
-  return result;
+    /* We cannot create the filestream, so ignore the incoming dataset and return an out-of-resources error to the SCU
+     */
+    DIC_UL bytesRead = 0;
+    DIC_UL pdvCount  = 0;
+    DCMNET_DEBUG("Ignoring incoming C-STORE dataset on presentation context "
+                 << OFstatic_cast(unsigned int, presID)
+                 << " with Affected SOP Instance UID: " << request.AffectedSOPInstanceUID);
+    OFCondition result = DIMSE_ignoreDataSet(m_assoc, m_blockMode, m_dimseTimeout, &bytesRead, &pdvCount);
+    if (result.good())
+    {
+        DCMNET_TRACE("Successfully skipped " << bytesRead << " bytes in " << pdvCount << " PDVs");
+    }
+    return result;
 }
 
-
-void DcmSCU::notifyInstanceStored(const OFString &filename,
-                                  const OFString &sopClassUID,
-                                  const OFString &sopInstanceUID) const
+void DcmSCU::notifyInstanceStored(const OFString& filename,
+                                  const OFString& sopClassUID,
+                                  const OFString& sopInstanceUID) const
 {
-  DCMNET_DEBUG("Stored instance to disk:");
-  DCMNET_DEBUG("  Filename: " << filename);
-  DCMNET_DEBUG("  SOP Class UID: " << sopClassUID);
-  DCMNET_DEBUG("  SOP Instance UID: " << sopInstanceUID);
+    DCMNET_DEBUG("Stored instance to disk:");
+    DCMNET_DEBUG("  Filename: " << filename);
+    DCMNET_DEBUG("  SOP Class UID: " << sopClassUID);
+    DCMNET_DEBUG("  SOP Instance UID: " << sopInstanceUID);
 }
 
-
 /* ************************************************************************* */
 /*                            C-FIND functionality                           */
 /* ************************************************************************* */
 
 // Sends a C-FIND Request on given presentation context
-OFCondition DcmSCU::sendFINDRequest(const T_ASC_PresentationContextID presID,
-                                    DcmDataset *queryKeys,
-                                    OFList<QRResponse*> *responses)
-{
-  // Do some basic validity checks
-  if (!isConnected())
-    return DIMSE_ILLEGALASSOCIATION;
-  if (queryKeys == NULL)
-    return DIMSE_NULLKEY;
-
-  /* Prepare DIMSE data structures for issuing request */
-  OFCondition cond;
-  OFString tempStr;
-  T_ASC_PresentationContextID pcid = presID;
-  T_DIMSE_Message msg;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&msg, sizeof(msg));
-
-  DcmDataset* statusDetail = NULL;
-  T_DIMSE_C_FindRQ* req = &(msg.msg.CFindRQ);
-  // Set type of message
-  msg.CommandField = DIMSE_C_FIND_RQ;
-  // Set message ID
-  req->MessageID = nextMessageID();
-  // Announce dataset
-  req->DataSetType = DIMSE_DATASET_PRESENT;
-  // Specify priority
-  req->Priority = DIMSE_PRIORITY_MEDIUM;
-
-  // Determine SOP Class from presentation context
-  OFString abstractSyntax, transferSyntax;
-  findPresentationContext(pcid, abstractSyntax, transferSyntax);
-  if (abstractSyntax.empty() || transferSyntax.empty())
-    return DIMSE_NOVALIDPRESENTATIONCONTEXTID;
-  OFStandard::strlcpy(req->AffectedSOPClassUID, abstractSyntax.c_str(), sizeof(req->AffectedSOPClassUID));
-
-  /* Send request */
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-  {
-    DCMNET_INFO("Sending C-FIND Request");
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, msg, DIMSE_OUTGOING, queryKeys, pcid));
-  } else {
-    DCMNET_INFO("Sending C-FIND Request (MsgID " << req->MessageID << ")");
-  }
-  cond = sendDIMSEMessage(pcid, &msg, queryKeys);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed sending C-FIND request: " << DimseCondition::dump(tempStr, cond));
-    return cond;
-  }
+OFCondition
+DcmSCU::sendFINDRequest(const T_ASC_PresentationContextID presID, DcmDataset* queryKeys, OFList<QRResponse*>* responses)
+{
+    // Do some basic validity checks
+    if (!isConnected())
+        return DIMSE_ILLEGALASSOCIATION;
+    if (queryKeys == NULL)
+        return DIMSE_NULLKEY;
 
-  /* Receive and handle response */
-  OFBool waitForNextResponse = OFTrue;
-  while (waitForNextResponse)
-  {
-    T_DIMSE_Message rsp;
+    /* Prepare DIMSE data structures for issuing request */
+    OFCondition cond;
+    OFString tempStr;
+    T_ASC_PresentationContextID pcid = presID;
+    T_DIMSE_Message msg;
     // Make sure everything is zeroed (especially options)
-    bzero((char*)&rsp, sizeof(rsp));
-
-    statusDetail = NULL;
+    bzero((char*)&msg, sizeof(msg));
+
+    DcmDataset* statusDetail = NULL;
+    T_DIMSE_C_FindRQ* req    = &(msg.msg.CFindRQ);
+    // Set type of message
+    msg.CommandField = DIMSE_C_FIND_RQ;
+    // Set message ID
+    req->MessageID = nextMessageID();
+    // Announce dataset
+    req->DataSetType = DIMSE_DATASET_PRESENT;
+    // Specify priority
+    req->Priority = DIMSE_PRIORITY_MEDIUM;
+
+    // Determine SOP Class from presentation context
+    OFString abstractSyntax, transferSyntax;
+    findPresentationContext(pcid, abstractSyntax, transferSyntax);
+    if (abstractSyntax.empty() || transferSyntax.empty())
+        return DIMSE_NOVALIDPRESENTATIONCONTEXTID;
+    OFStandard::strlcpy(req->AffectedSOPClassUID, abstractSyntax.c_str(), sizeof(req->AffectedSOPClassUID));
 
-    // Receive command set
-    cond = receiveDIMSECommand(&pcid, &rsp, &statusDetail, NULL /* not interested in the command set */);
-    if (cond.bad())
+    /* Send request */
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
     {
-      DCMNET_ERROR("Failed receiving DIMSE response: " << DimseCondition::dump(tempStr, cond));
-      return cond;
+        DCMNET_INFO("Sending C-FIND Request");
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, msg, DIMSE_OUTGOING, queryKeys, pcid));
     }
-
-    if (rsp.CommandField == DIMSE_C_FIND_RSP)
+    else
     {
-      if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-      {
-        DCMNET_INFO("Received C-FIND Response");
-        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
-      } else {
-        DCMNET_INFO("Received C-FIND Response (" << DU_cfindStatusString(rsp.msg.CFindRSP.DimseStatus) << ")");
-      }
-    } else {
-      DCMNET_ERROR("Expected C-FIND response but received DIMSE command 0x"
-        << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
-        << OFstatic_cast(unsigned int, rsp.CommandField));
-      DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
-      delete statusDetail;
-      return DIMSE_BADCOMMANDTYPE;
-    }
-
-    // Prepare response package for response handler
-    OFunique_ptr<QRResponse> findRSP(new QRResponse);
-    findRSP->m_affectedSOPClassUID = rsp.msg.CFindRSP.AffectedSOPClassUID;
-    findRSP->m_messageIDRespondedTo = rsp.msg.CFindRSP.MessageIDBeingRespondedTo;
-    findRSP->m_status = rsp.msg.CFindRSP.DimseStatus;
-    findRSP->m_statusDetail = statusDetail;
-
-    // Receive dataset if there is one (status PENDING)
-    DcmDataset *rspDataset = NULL;
-    if (DICOM_PENDING_STATUS(findRSP->m_status))
-    {
-      // Check if dataset is announced correctly
-      if (rsp.msg.CFindRSP.DataSetType == DIMSE_DATASET_NULL)
-      {
-        DCMNET_ERROR("Received C-FIND response with PENDING status but no dataset announced, aborting");
-        return DIMSE_BADMESSAGE;
-      }
-
-      // Receive dataset
-      cond = receiveDIMSEDataset(&pcid, &rspDataset);
-      if (cond.bad())
-        return DIMSE_BADDATA;
-      findRSP->m_dataset = rspDataset;
+        DCMNET_INFO("Sending C-FIND Request (MsgID " << req->MessageID << ")");
     }
-
-    // Handle C-FIND response (has to handle all possible status flags)
-    cond = handleFINDResponse(pcid, findRSP.get(), waitForNextResponse);
+    cond = sendDIMSEMessage(pcid, &msg, queryKeys);
     if (cond.bad())
     {
-      DCMNET_WARN("Unable to handle C-FIND response correctly: " << cond.text() << " (ignored)");
-      // don't return here but trust the "waitForNextResponse" variable
+        DCMNET_ERROR("Failed sending C-FIND request: " << DimseCondition::dump(tempStr, cond));
+        return cond;
     }
-    // if response could be handled successfully, add it to response list
-    else
+
+    /* Receive and handle response */
+    OFBool waitForNextResponse = OFTrue;
+    while (waitForNextResponse)
     {
-      if (responses != NULL) // only add if desired by caller
-        responses->push_back(findRSP.release());
+        T_DIMSE_Message rsp;
+        // Make sure everything is zeroed (especially options)
+        bzero((char*)&rsp, sizeof(rsp));
+
+        statusDetail = NULL;
+
+        // Receive command set
+        cond = receiveDIMSECommand(&pcid, &rsp, &statusDetail, NULL /* not interested in the command set */);
+        if (cond.bad())
+        {
+            DCMNET_ERROR("Failed receiving DIMSE response: " << DimseCondition::dump(tempStr, cond));
+            return cond;
+        }
+
+        if (rsp.CommandField == DIMSE_C_FIND_RSP)
+        {
+            if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+            {
+                DCMNET_INFO("Received C-FIND Response");
+                DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
+            }
+            else
+            {
+                DCMNET_INFO("Received C-FIND Response (" << DU_cfindStatusString(rsp.msg.CFindRSP.DimseStatus) << ")");
+            }
+        }
+        else
+        {
+            DCMNET_ERROR("Expected C-FIND response but received DIMSE command 0x"
+                         << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
+                         << OFstatic_cast(unsigned int, rsp.CommandField));
+            DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, rsp, DIMSE_INCOMING, NULL, pcid));
+            delete statusDetail;
+            return DIMSE_BADCOMMANDTYPE;
+        }
+
+        // Prepare response package for response handler
+        OFunique_ptr<QRResponse> findRSP(new QRResponse);
+        findRSP->m_affectedSOPClassUID  = rsp.msg.CFindRSP.AffectedSOPClassUID;
+        findRSP->m_messageIDRespondedTo = rsp.msg.CFindRSP.MessageIDBeingRespondedTo;
+        findRSP->m_status               = rsp.msg.CFindRSP.DimseStatus;
+        findRSP->m_statusDetail         = statusDetail;
+
+        // Receive dataset if there is one (status PENDING)
+        DcmDataset* rspDataset = NULL;
+        if (DICOM_PENDING_STATUS(findRSP->m_status))
+        {
+            // Check if dataset is announced correctly
+            if (rsp.msg.CFindRSP.DataSetType == DIMSE_DATASET_NULL)
+            {
+                DCMNET_ERROR("Received C-FIND response with PENDING status but no dataset announced, aborting");
+                return DIMSE_BADMESSAGE;
+            }
+
+            // Receive dataset
+            cond = receiveDIMSEDataset(&pcid, &rspDataset);
+            if (cond.bad())
+                return DIMSE_BADDATA;
+            findRSP->m_dataset = rspDataset;
+        }
+
+        // Handle C-FIND response (has to handle all possible status flags)
+        cond = handleFINDResponse(pcid, findRSP.get(), waitForNextResponse);
+        if (cond.bad())
+        {
+            DCMNET_WARN("Unable to handle C-FIND response correctly: " << cond.text() << " (ignored)");
+            // don't return here but trust the "waitForNextResponse" variable
+        }
+        // if response could be handled successfully, add it to response list
+        else
+        {
+            if (responses != NULL) // only add if desired by caller
+                responses->push_back(findRSP.release());
+        }
     }
-  }
-  /* All responses received or break signal occurred */
-  return EC_Normal;
+    /* All responses received or break signal occurred */
+    return EC_Normal;
 }
 
-
 // Standard handler for C-FIND message responses
 OFCondition DcmSCU::handleFINDResponse(const T_ASC_PresentationContextID /* presID */,
-                                       QRResponse *response,
-                                       OFBool &waitForNextResponse)
-{
-  if (!isConnected())
-    return DIMSE_ILLEGALASSOCIATION;
-  if (response == NULL)
-    return DIMSE_NULLKEY;
-
-  DCMNET_DEBUG("Handling C-FIND Response");
-  switch (response->m_status) {
-    case STATUS_Pending:
-    case STATUS_FIND_Pending_WarningUnsupportedOptionalKeys:
-      /* in this case the current C-FIND-RSP indicates that */
-      /* there will be some more results */
-      waitForNextResponse = OFTrue;
-      DCMNET_DEBUG("One or more pending C-FIND responses");
-      break;
-    case STATUS_Success:
-      /* in this case the current C-FIND-RSP indicates that */
-      /* there are no more records that match the search mask */
-      waitForNextResponse = OFFalse;
-      DCMNET_DEBUG("Received final C-FIND response, no more C-FIND responses expected");
-      break;
-    default:
-      /* in all other cases, don't expect further responses to come */
-      waitForNextResponse = OFFalse;
-      DCMNET_DEBUG("Status tells not to wait for further C-FIND responses");
-      break;
-  } //switch
-  return EC_Normal;
-}
+                                       QRResponse* response,
+                                       OFBool& waitForNextResponse)
+{
+    waitForNextResponse = OFFalse;
+    if (response == NULL)
+        return DIMSE_NULLKEY;
 
+    DCMNET_DEBUG("Handling C-FIND Response");
+    OFString s;
+    s = DU_cfindStatusString(response->m_status);
+    return handleSessionResponseDefault(response->m_status, s, waitForNextResponse);
+}
 
 /* ************************************************************************* */
 /*                            C-CANCEL functionality                         */
@@ -1692,56 +1612,57 @@ OFCondition DcmSCU::handleFINDResponse(const T_ASC_PresentationContextID /* pres
 // Send C-CANCEL-REQ and, therefore, ends current C-FIND, -MOVE or -GET session
 OFCondition DcmSCU::sendCANCELRequest(const T_ASC_PresentationContextID presID)
 {
-  if (!isConnected())
-    return DIMSE_ILLEGALASSOCIATION;
-
-  /* Prepare DIMSE data structures for issuing request */
-  OFCondition cond;
-  OFString tempStr;
-  T_ASC_PresentationContextID pcid = presID;
-  T_DIMSE_Message msg;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&msg, sizeof(msg));
-  T_DIMSE_C_CancelRQ* req = &(msg.msg.CCancelRQ);
-  // Set type of message
-  msg.CommandField = DIMSE_C_CANCEL_RQ;
-  /* Set message ID responded to. A new message ID is _not_ needed so
-     we do not increment the message ID here but instead have to give the
-     message ID that was used last.
-     Note that that it is required to actually use the message ID of the last
-     C-FIND/GET/MOVE that was issued on this presentation context channel.
-     However, since we only support synchronous association mode so far,
-     it is enough to take the last message ID used at all.
-     For asynchronous operation, we would have to lookup the message ID
-     of the last C-FIND/GET/MOVE request issued and thus, store this
-     information after sending it.
-   */
-  req->MessageIDBeingRespondedTo = m_assoc->nextMsgID - 1;
-  // Announce dataset
-  req->DataSetType = DIMSE_DATASET_NULL;
-
-  /* We do not care about the transfer syntax since no
-     dataset is transported at all, i.e. we trust that the user provided
-     the correct presentation context ID (could be private one).
-   */
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-  {
-    DCMNET_INFO("Sending C-CANCEL Request");
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, msg, DIMSE_OUTGOING, NULL, pcid));
-  } else {
-    DCMNET_INFO("Sending C-CANCEL Request (MsgID " << req->MessageIDBeingRespondedTo
-      << ", PresID " << OFstatic_cast(unsigned int, pcid) <<  ")");
-  }
-  cond = sendDIMSEMessage(pcid, &msg, NULL /*dataObject*/);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed sending C-CANCEL request: " << DimseCondition::dump(tempStr, cond));
-  }
+    if (!isConnected())
+        return DIMSE_ILLEGALASSOCIATION;
 
-  DCMNET_TRACE("There is no C-CANCEL response in DICOM, so none expected");
-  return cond;
-}
+    /* Prepare DIMSE data structures for issuing request */
+    OFCondition cond;
+    OFString tempStr;
+    T_ASC_PresentationContextID pcid = presID;
+    T_DIMSE_Message msg;
+    // Make sure everything is zeroed (especially options)
+    bzero((char*)&msg, sizeof(msg));
+    T_DIMSE_C_CancelRQ* req = &(msg.msg.CCancelRQ);
+    // Set type of message
+    msg.CommandField = DIMSE_C_CANCEL_RQ;
+    /* Set message ID responded to. A new message ID is _not_ needed so
+       we do not increment the message ID here but instead have to give the
+       message ID that was used last.
+       Note that that it is required to actually use the message ID of the last
+       C-FIND/GET/MOVE that was issued on this presentation context channel.
+       However, since we only support synchronous association mode so far,
+       it is enough to take the last message ID used at all.
+       For asynchronous operation, we would have to lookup the message ID
+       of the last C-FIND/GET/MOVE request issued and thus, store this
+       information after sending it.
+     */
+    req->MessageIDBeingRespondedTo = m_assoc->nextMsgID - 1;
+    // Announce dataset
+    req->DataSetType = DIMSE_DATASET_NULL;
+
+    /* We do not care about the transfer syntax since no
+       dataset is transported at all, i.e. we trust that the user provided
+       the correct presentation context ID (could be private one).
+     */
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+    {
+        DCMNET_INFO("Sending C-CANCEL Request");
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, msg, DIMSE_OUTGOING, NULL, pcid));
+    }
+    else
+    {
+        DCMNET_INFO("Sending C-CANCEL Request (MsgID " << req->MessageIDBeingRespondedTo << ", PresID "
+                                                       << OFstatic_cast(unsigned int, pcid) << ")");
+    }
+    cond = sendDIMSEMessage(pcid, &msg, NULL /*dataObject*/);
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Failed sending C-CANCEL request: " << DimseCondition::dump(tempStr, cond));
+    }
 
+    DCMNET_TRACE("There is no C-CANCEL response in DICOM, so none expected");
+    return cond;
+}
 
 /* ************************************************************************* */
 /*                            N-ACTION functionality                         */
@@ -1749,392 +1670,444 @@ OFCondition DcmSCU::sendCANCELRequest(const T_ASC_PresentationContextID presID)
 
 // Sends N-ACTION request to another DICOM application
 OFCondition DcmSCU::sendACTIONRequest(const T_ASC_PresentationContextID presID,
-                                      const OFString &sopInstanceUID,
+                                      const OFStringsopInstanceUID,
                                       const Uint16 actionTypeID,
-                                      DcmDataset *reqDataset,
-                                      Uint16 &rspStatusCode)
-{
-  // Do some basic validity checks
-  if (!isConnected())
-    return DIMSE_ILLEGALASSOCIATION;
-  if (sopInstanceUID.empty() || (reqDataset == NULL))
-    return DIMSE_NULLKEY;
-
-  // Prepare DIMSE data structures for issuing request
-  OFCondition cond;
-  OFString tempStr;
-  T_ASC_PresentationContextID pcid = presID;
-  T_DIMSE_Message request;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&request, sizeof(request));
-  T_DIMSE_N_ActionRQ &actionReq = request.msg.NActionRQ;
-  DcmDataset *statusDetail = NULL;
-
-  request.CommandField = DIMSE_N_ACTION_RQ;
-  actionReq.MessageID = nextMessageID();
-  actionReq.DataSetType = DIMSE_DATASET_PRESENT;
-  actionReq.ActionTypeID = actionTypeID;
-
-  // Determine SOP Class from presentation context
-  OFString abstractSyntax, transferSyntax;
-  findPresentationContext(pcid, abstractSyntax, transferSyntax);
-  if (abstractSyntax.empty() || transferSyntax.empty())
-    return DIMSE_NOVALIDPRESENTATIONCONTEXTID;
-  OFStandard::strlcpy(actionReq.RequestedSOPClassUID, abstractSyntax.c_str(), sizeof(actionReq.RequestedSOPClassUID));
-  OFStandard::strlcpy(actionReq.RequestedSOPInstanceUID, sopInstanceUID.c_str(), sizeof(actionReq.RequestedSOPInstanceUID));
-
-  // Send request
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-  {
-    DCMNET_INFO("Sending N-ACTION Request");
-    // Output dataset only if trace level is enabled
-    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
-      DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_OUTGOING, reqDataset, pcid));
+                                      DcmDataset* reqDataset,
+                                      Uint16& rspStatusCode)
+{
+    // Do some basic validity checks
+    if (!isConnected())
+        return DIMSE_ILLEGALASSOCIATION;
+    if (sopInstanceUID.empty() || (reqDataset == NULL))
+        return DIMSE_NULLKEY;
+
+    // Prepare DIMSE data structures for issuing request
+    OFCondition cond;
+    OFString tempStr;
+    T_ASC_PresentationContextID pcid = presID;
+    T_DIMSE_Message request;
+    // Make sure everything is zeroed (especially options)
+    bzero((char*)&request, sizeof(request));
+    T_DIMSE_N_ActionRQ& actionReq = request.msg.NActionRQ;
+    DcmDataset* statusDetail      = NULL;
+
+    request.CommandField   = DIMSE_N_ACTION_RQ;
+    actionReq.MessageID    = nextMessageID();
+    actionReq.DataSetType  = DIMSE_DATASET_PRESENT;
+    actionReq.ActionTypeID = actionTypeID;
+
+    // Determine SOP Class from presentation context
+    OFString abstractSyntax, transferSyntax;
+    findPresentationContext(pcid, abstractSyntax, transferSyntax);
+    if (abstractSyntax.empty() || transferSyntax.empty())
+        return DIMSE_NOVALIDPRESENTATIONCONTEXTID;
+    OFStandard::strlcpy(actionReq.RequestedSOPClassUID, abstractSyntax.c_str(), sizeof(actionReq.RequestedSOPClassUID));
+    OFStandard::strlcpy(
+        actionReq.RequestedSOPInstanceUID, sopInstanceUID.c_str(), sizeof(actionReq.RequestedSOPInstanceUID));
+
+    // Send request
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+    {
+        DCMNET_INFO("Sending N-ACTION Request");
+        // Output dataset only if trace level is enabled
+        if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
+            DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_OUTGOING, reqDataset, pcid));
+        else
+            DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_OUTGOING, NULL, pcid));
+    }
     else
-      DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_OUTGOING, NULL, pcid));
-  } else {
-    DCMNET_INFO("Sending N-ACTION Request (MsgID " << actionReq.MessageID << ")");
-  }
-  cond = sendDIMSEMessage(pcid, &request, reqDataset);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed sending N-ACTION request: " << DimseCondition::dump(tempStr, cond));
-    return cond;
-  }
+    {
+        DCMNET_INFO("Sending N-ACTION Request (MsgID " << actionReq.MessageID << ")");
+    }
+    cond = sendDIMSEMessage(pcid, &request, reqDataset);
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Failed sending N-ACTION request: " << DimseCondition::dump(tempStr, cond));
+        return cond;
+    }
 
-  // Receive response
-  T_DIMSE_Message response;
-  bzero((char*)&response, sizeof(response));
-  cond = receiveDIMSECommand(&pcid, &response, &statusDetail, NULL /* commandSet */);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed receiving DIMSE response: " << DimseCondition::dump(tempStr, cond));
-    return cond;
-  }
+    // Receive response
+    T_DIMSE_Message response;
+    bzero((char*)&response, sizeof(response));
+    cond = receiveDIMSECommand(&pcid, &response, &statusDetail, NULL /* commandSet */);
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Failed receiving DIMSE response: " << DimseCondition::dump(tempStr, cond));
+        return cond;
+    }
 
-  // Check command set
-  if (response.CommandField == DIMSE_N_ACTION_RSP)
-  {
-    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+    // Check command set
+    if (response.CommandField == DIMSE_N_ACTION_RSP)
     {
-      DCMNET_INFO("Received N-ACTION Response");
-      DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_INCOMING, NULL, pcid));
-    } else {
-      DCMNET_INFO("Received N-ACTION Response (" << DU_nactionStatusString(response.msg.NActionRSP.DimseStatus) << ")");
-    }
-  } else {
-    DCMNET_ERROR("Expected N-ACTION response but received DIMSE command 0x"
-      << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
-      << OFstatic_cast(unsigned int, response.CommandField));
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_INCOMING, NULL, pcid));
-    delete statusDetail;
-    return DIMSE_BADCOMMANDTYPE;
-  }
-  if (statusDetail != NULL)
-  {
-    DCMNET_DEBUG("Response has status detail:" << OFendl << DcmObject::PrintHelper(*statusDetail));
-    delete statusDetail;
-  }
+        if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+        {
+            DCMNET_INFO("Received N-ACTION Response");
+            DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_INCOMING, NULL, pcid));
+        }
+        else
+        {
+            DCMNET_INFO("Received N-ACTION Response (" << DU_nactionStatusString(response.msg.NActionRSP.DimseStatus)
+                                                       << ")");
+        }
+    }
+    else
+    {
+        DCMNET_ERROR("Expected N-ACTION response but received DIMSE command 0x"
+                     << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
+                     << OFstatic_cast(unsigned int, response.CommandField));
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_INCOMING, NULL, pcid));
+        delete statusDetail;
+        return DIMSE_BADCOMMANDTYPE;
+    }
+    if (statusDetail != NULL)
+    {
+        DCMNET_DEBUG("Response has status detail:" << OFendl << DcmObject::PrintHelper(*statusDetail));
+        delete statusDetail;
+    }
 
-  // Set return value
-  T_DIMSE_N_ActionRSP &actionRsp = response.msg.NActionRSP;
-  rspStatusCode = actionRsp.DimseStatus;
+    // Set return value
+    T_DIMSE_N_ActionRSP& actionRsp = response.msg.NActionRSP;
+    rspStatusCode                  = actionRsp.DimseStatus;
 
-  // Check whether there is a dataset to be received
-  if (actionRsp.DataSetType == DIMSE_DATASET_PRESENT)
-  {
-    // this should never happen
-    DcmDataset *tempDataset = NULL;
-    T_ASC_PresentationContextID tempID;
-    DCMNET_WARN("Trying to retrieve unexpected dataset in N-ACTION response");
-    cond = receiveDIMSEDataset(&tempID, &tempDataset);
-    if (cond.good())
+    // Check whether there is a dataset to be received
+    if (actionRsp.DataSetType == DIMSE_DATASET_PRESENT)
+    {
+        // this should never happen
+        DcmDataset* tempDataset = NULL;
+        T_ASC_PresentationContextID tempID;
+        DCMNET_WARN("Trying to retrieve unexpected dataset in N-ACTION response");
+        cond = receiveDIMSEDataset(&tempID, &tempDataset);
+        if (cond.good())
+        {
+            DCMNET_WARN("Received unexpected dataset after N-ACTION response, ignoring");
+            delete tempDataset;
+        }
+        else
+        {
+            return DIMSE_BADDATA;
+        }
+    }
+    if (actionRsp.MessageIDBeingRespondedTo != actionReq.MessageID)
     {
-      DCMNET_WARN("Received unexpected dataset after N-ACTION response, ignoring");
-      delete tempDataset;
-    } else {
-      return DIMSE_BADDATA;
+        // since we only support synchronous communication, the message ID in the response
+        // should be identical to the one in the request
+        DCMNET_ERROR("Received response with wrong message ID (" << actionRsp.MessageIDBeingRespondedTo
+                                                                 << " instead of " << actionReq.MessageID << ")");
+        return DIMSE_BADMESSAGE;
     }
-  }
-  if (actionRsp.MessageIDBeingRespondedTo != actionReq.MessageID)
-  {
-    // since we only support synchronous communication, the message ID in the response
-    // should be identical to the one in the request
-    DCMNET_ERROR("Received response with wrong message ID (" << actionRsp.MessageIDBeingRespondedTo
-      << " instead of " << actionReq.MessageID << ")");
-    return DIMSE_BADMESSAGE;
-  }
 
-  return cond;
+    return cond;
 }
 
-
 /* ************************************************************************* */
 /*                         N-EVENT REPORT functionality                      */
 /* ************************************************************************* */
 
 // Sends N-EVENT-REPORT request and receives N-EVENT-REPORT response
 OFCondition DcmSCU::sendEVENTREPORTRequest(const T_ASC_PresentationContextID presID,
-                                           const OFString &sopInstanceUID,
+                                           const OFStringsopInstanceUID,
                                            const Uint16 eventTypeID,
-                                           DcmDataset *reqDataset,
-                                           Uint16 &rspStatusCode)
-{
-  // Do some basic validity checks
-  if (!isConnected())
-    return DIMSE_ILLEGALASSOCIATION;
-  if (sopInstanceUID.empty() || (reqDataset == NULL))
-    return DIMSE_NULLKEY;
-
-  // Prepare DIMSE data structures for issuing request
-  OFCondition cond;
-  OFString tempStr;
-  T_ASC_PresentationContextID pcid = presID;
-  T_DIMSE_Message request;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&request, sizeof(request));
-
-  T_DIMSE_N_EventReportRQ &eventReportReq = request.msg.NEventReportRQ;
-  DcmDataset *statusDetail = NULL;
-
-  request.CommandField = DIMSE_N_EVENT_REPORT_RQ;
-
-  // Generate a new message ID
-  eventReportReq.MessageID = nextMessageID();
-  eventReportReq.DataSetType = DIMSE_DATASET_PRESENT;
-  eventReportReq.EventTypeID = eventTypeID;
-
-  // Determine SOP Class from presentation context
-  OFString abstractSyntax, transferSyntax;
-  findPresentationContext(pcid, abstractSyntax, transferSyntax);
-  if (abstractSyntax.empty() || transferSyntax.empty())
-    return DIMSE_NOVALIDPRESENTATIONCONTEXTID;
-  OFStandard::strlcpy(eventReportReq.AffectedSOPClassUID, abstractSyntax.c_str(), sizeof(eventReportReq.AffectedSOPClassUID));
-  OFStandard::strlcpy(eventReportReq.AffectedSOPInstanceUID, sopInstanceUID.c_str(), sizeof(eventReportReq.AffectedSOPInstanceUID));
-
-  // Send request
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-  {
-    DCMNET_INFO("Sending N-EVENT-REPORT Request");
-    // Output dataset only if trace level is enabled
-    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
-      DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_OUTGOING, reqDataset, pcid));
-    else
-      DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_OUTGOING, NULL, pcid));
-  } else {
-    DCMNET_INFO("Sending N-EVENT-REPORT Request (MsgID " << eventReportReq.MessageID << ")");
-  }
-  cond = sendDIMSEMessage(pcid, &request, reqDataset);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed sending N-EVENT-REPORT request: " << DimseCondition::dump(tempStr, cond));
-    return cond;
-  }
-  // Receive response
-  T_DIMSE_Message response;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&response, sizeof(response));
+                                           DcmDataset* reqDataset,
+                                           Uint16& rspStatusCode)
+{
+    // Do some basic validity checks
+    if (!isConnected())
+        return DIMSE_ILLEGALASSOCIATION;
+    if (sopInstanceUID.empty() || (reqDataset == NULL))
+        return DIMSE_NULLKEY;
 
-  cond = receiveDIMSECommand(&pcid, &response, &statusDetail, NULL /* commandSet */);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed receiving DIMSE response: " << DimseCondition::dump(tempStr, cond));
-    return cond;
-  }
+    // Prepare DIMSE data structures for issuing request
+    OFCondition cond;
+    OFString tempStr;
+    T_ASC_PresentationContextID pcid = presID;
+    T_DIMSE_Message request;
+    // Make sure everything is zeroed (especially options)
+    bzero((char*)&request, sizeof(request));
 
-  // Check command set
-  if (response.CommandField == DIMSE_N_EVENT_REPORT_RSP)
-  {
+    T_DIMSE_N_EventReportRQ& eventReportReq = request.msg.NEventReportRQ;
+    DcmDataset* statusDetail                = NULL;
+
+    request.CommandField = DIMSE_N_EVENT_REPORT_RQ;
+
+    // Generate a new message ID
+    eventReportReq.MessageID   = nextMessageID();
+    eventReportReq.DataSetType = DIMSE_DATASET_PRESENT;
+    eventReportReq.EventTypeID = eventTypeID;
+
+    // Determine SOP Class from presentation context
+    OFString abstractSyntax, transferSyntax;
+    findPresentationContext(pcid, abstractSyntax, transferSyntax);
+    if (abstractSyntax.empty() || transferSyntax.empty())
+        return DIMSE_NOVALIDPRESENTATIONCONTEXTID;
+    OFStandard::strlcpy(
+        eventReportReq.AffectedSOPClassUID, abstractSyntax.c_str(), sizeof(eventReportReq.AffectedSOPClassUID));
+    OFStandard::strlcpy(
+        eventReportReq.AffectedSOPInstanceUID, sopInstanceUID.c_str(), sizeof(eventReportReq.AffectedSOPInstanceUID));
+
+    // Send request
     if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
     {
-      DCMNET_INFO("Received N-EVENT-REPORT Response");
-      DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_INCOMING, NULL, pcid));
-    } else {
-      DCMNET_INFO("Received N-EVENT-REPORT Response (" << DU_neventReportStatusString(response.msg.NEventReportRSP.DimseStatus) << ")");
-    }
-  } else {
-    DCMNET_ERROR("Expected N-EVENT-REPORT response but received DIMSE command 0x"
-      << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
-      << OFstatic_cast(unsigned int, response.CommandField));
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_INCOMING, NULL, pcid));
-    delete statusDetail;
-    return DIMSE_BADCOMMANDTYPE;
-  }
-  if (statusDetail != NULL)
-  {
-    DCMNET_DEBUG("Response has status detail:" << OFendl << DcmObject::PrintHelper(*statusDetail));
-    delete statusDetail;
-  }
+        DCMNET_INFO("Sending N-EVENT-REPORT Request");
+        // Output dataset only if trace level is enabled
+        if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
+            DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_OUTGOING, reqDataset, pcid));
+        else
+            DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_OUTGOING, NULL, pcid));
+    }
+    else
+    {
+        DCMNET_INFO("Sending N-EVENT-REPORT Request (MsgID " << eventReportReq.MessageID << ")");
+    }
+    cond = sendDIMSEMessage(pcid, &request, reqDataset);
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Failed sending N-EVENT-REPORT request: " << DimseCondition::dump(tempStr, cond));
+        return cond;
+    }
+    // Receive response
+    T_DIMSE_Message response;
+    // Make sure everything is zeroed (especially options)
+    bzero((char*)&response, sizeof(response));
 
-  // Set return value
-  T_DIMSE_N_EventReportRSP &eventReportRsp = response.msg.NEventReportRSP;
-  rspStatusCode = eventReportRsp.DimseStatus;
+    cond = receiveDIMSECommand(&pcid, &response, &statusDetail, NULL /* commandSet */);
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Failed receiving DIMSE response: " << DimseCondition::dump(tempStr, cond));
+        return cond;
+    }
 
-  // Check whether there is a dataset to be received
-  if (eventReportRsp.DataSetType == DIMSE_DATASET_PRESENT)
-  {
-    // this should never happen
-    DcmDataset *tempDataset = NULL;
-    T_ASC_PresentationContextID tempID;
-    cond = receiveDIMSEDataset(&tempID, &tempDataset);
-    if (cond.good())
+    // Check command set
+    if (response.CommandField == DIMSE_N_EVENT_REPORT_RSP)
+    {
+        if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+        {
+            DCMNET_INFO("Received N-EVENT-REPORT Response");
+            DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_INCOMING, NULL, pcid));
+        }
+        else
+        {
+            DCMNET_INFO("Received N-EVENT-REPORT Response ("
+                        << DU_neventReportStatusString(response.msg.NEventReportRSP.DimseStatus) << ")");
+        }
+    }
+    else
     {
-      DCMNET_WARN("Received unexpected dataset after N-EVENT-REPORT response, ignoring");
-      delete tempDataset;
-    } else {
-      DCMNET_ERROR("Failed receiving unexpected dataset after N-EVENT-REPORT response: "
-        << DimseCondition::dump(tempStr, cond));
-      return DIMSE_BADDATA;
+        DCMNET_ERROR("Expected N-EVENT-REPORT response but received DIMSE command 0x"
+                     << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
+                     << OFstatic_cast(unsigned int, response.CommandField));
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_INCOMING, NULL, pcid));
+        delete statusDetail;
+        return DIMSE_BADCOMMANDTYPE;
+    }
+    if (statusDetail != NULL)
+    {
+        DCMNET_DEBUG("Response has status detail:" << OFendl << DcmObject::PrintHelper(*statusDetail));
+        delete statusDetail;
     }
-  }
 
-  // Check whether the message ID being responded to is equal to the message ID of the request
-  if (eventReportRsp.MessageIDBeingRespondedTo != eventReportReq.MessageID)
-  {
-    DCMNET_ERROR("Received response with wrong message ID (" << eventReportRsp.MessageIDBeingRespondedTo
-      << " instead of " << eventReportReq.MessageID << ")");
-    return DIMSE_BADMESSAGE;
-  }
-  return cond;
+    // Set return value
+    T_DIMSE_N_EventReportRSP& eventReportRsp = response.msg.NEventReportRSP;
+    rspStatusCode                            = eventReportRsp.DimseStatus;
+
+    // Check whether there is a dataset to be received
+    if (eventReportRsp.DataSetType == DIMSE_DATASET_PRESENT)
+    {
+        // this should never happen
+        DcmDataset* tempDataset = NULL;
+        T_ASC_PresentationContextID tempID;
+        cond = receiveDIMSEDataset(&tempID, &tempDataset);
+        if (cond.good())
+        {
+            DCMNET_WARN("Received unexpected dataset after N-EVENT-REPORT response, ignoring");
+            delete tempDataset;
+        }
+        else
+        {
+            DCMNET_ERROR("Failed receiving unexpected dataset after N-EVENT-REPORT response: "
+                         << DimseCondition::dump(tempStr, cond));
+            return DIMSE_BADDATA;
+        }
+    }
+
+    // Check whether the message ID being responded to is equal to the message ID of the request
+    if (eventReportRsp.MessageIDBeingRespondedTo != eventReportReq.MessageID)
+    {
+        DCMNET_ERROR("Received response with wrong message ID (" << eventReportRsp.MessageIDBeingRespondedTo
+                                                                 << " instead of " << eventReportReq.MessageID << ")");
+        return DIMSE_BADMESSAGE;
+    }
+    return cond;
 }
 
 // Receives N-EVENT-REPORT request
-OFCondition DcmSCU::handleEVENTREPORTRequest(DcmDataset *&reqDataset,
-                                             Uint16 &eventTypeID,
-                                             const int timeout)
-{
-  // Do some basic validity checks
-  if (!isConnected())
-    return DIMSE_ILLEGALASSOCIATION;
-
-  OFCondition cond;
-  OFString tempStr;
-  T_ASC_PresentationContextID presID;
-  T_ASC_PresentationContextID presIDdset;
-  T_DIMSE_Message request;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&request, sizeof(request));
-  T_DIMSE_N_EventReportRQ &eventReportReq = request.msg.NEventReportRQ;
-  DcmDataset *dataset = NULL;
-  DcmDataset *statusDetail = NULL;
-  Uint16 statusCode = 0;
-
-  if (timeout > 0)
-    DCMNET_DEBUG("Handle N-EVENT-REPORT request, waiting up to " << timeout << " seconds (only for N-EVENT-REPORT message)");
-  else if ((m_dimseTimeout > 0) && (m_blockMode == DIMSE_NONBLOCKING))
-    DCMNET_DEBUG("Handle N-EVENT-REPORT request, waiting up to " << m_dimseTimeout << " seconds (default for all DIMSE messages)");
-  else
-    DCMNET_DEBUG("Handle N-EVENT-REPORT request, waiting an unlimited period of time");
-
-  // Receive request, use specific timeout (if defined)
-  cond = receiveDIMSECommand(&presID, &request, &statusDetail, NULL /* commandSet */, timeout);
-  if (cond.bad())
-  {
-    if (cond != DIMSE_NODATAAVAILABLE)
-      DCMNET_ERROR("Failed receiving DIMSE request: " << DimseCondition::dump(tempStr, cond));
-    return cond;
-  }
+OFCondition DcmSCU::handleEVENTREPORTRequest(DcmDataset*& reqDataset, Uint16& eventTypeID, const int timeout)
+{
+    // Do some basic validity checks
+    if (!isConnected())
+        return DIMSE_ILLEGALASSOCIATION;
 
-  // Check command set
-  if (request.CommandField == DIMSE_N_EVENT_REPORT_RQ)
-  {
-    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-      DCMNET_INFO("Received N-EVENT-REPORT Request");
+    OFCondition cond;
+    OFString tempStr;
+    T_ASC_PresentationContextID presID;
+    T_ASC_PresentationContextID presIDdset;
+    T_DIMSE_Message request;
+    // Make sure everything is zeroed (especially options)
+    bzero((char*)&request, sizeof(request));
+    T_DIMSE_N_EventReportRQ& eventReportReq = request.msg.NEventReportRQ;
+    DcmDataset* dataset                     = NULL;
+    DcmDataset* statusDetail                = NULL;
+    Uint16 statusCode                       = 0;
+
+    if (timeout > 0)
+        DCMNET_DEBUG("Handle N-EVENT-REPORT request, waiting up to " << timeout
+                                                                     << " seconds (only for N-EVENT-REPORT message)");
+    else if ((m_dimseTimeout > 0) && (m_blockMode == DIMSE_NONBLOCKING))
+        DCMNET_DEBUG("Handle N-EVENT-REPORT request, waiting up to " << m_dimseTimeout
+                                                                     << " seconds (default for all DIMSE messages)");
     else
-      DCMNET_INFO("Received N-EVENT-REPORT Request (MsgID " << eventReportReq.MessageID << ")");
-  } else {
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_INCOMING, NULL, presID));
-    DCMNET_ERROR("Expected N-EVENT-REPORT request but received DIMSE command 0x"
-      << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
-      << OFstatic_cast(unsigned int, request.CommandField));
-    delete statusDetail;
-    return DIMSE_BADCOMMANDTYPE;
-  }
-  if (statusDetail != NULL)
-  {
-    DCMNET_DEBUG("Request has status detail:" << OFendl << DcmObject::PrintHelper(*statusDetail));
-    delete statusDetail;
-  }
+        DCMNET_DEBUG("Handle N-EVENT-REPORT request, waiting an unlimited period of time");
 
-  // Check if dataset is announced correctly
-  if (eventReportReq.DataSetType == DIMSE_DATASET_NULL)
-  {
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_INCOMING, NULL, presID));
-    DCMNET_ERROR("Received N-EVENT-REPORT request but no dataset announced, aborting");
-    return DIMSE_BADMESSAGE;
-  }
+    // Receive request, use specific timeout (if defined)
+    cond = receiveDIMSECommand(&presID, &request, &statusDetail, NULL /* commandSet */, timeout);
+    if (cond.bad())
+    {
+        if (cond != DIMSE_NODATAAVAILABLE)
+            DCMNET_ERROR("Failed receiving DIMSE request: " << DimseCondition::dump(tempStr, cond));
+        return cond;
+    }
 
-  // Receive dataset
-  cond = receiveDIMSEDataset(&presIDdset, &dataset);
-  if (cond.bad())
-  {
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_INCOMING, NULL, presID));
-    return DIMSE_BADDATA;
-  }
+    // Check command set
+    if (request.CommandField == DIMSE_N_EVENT_REPORT_RQ)
+    {
+        if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+            DCMNET_INFO("Received N-EVENT-REPORT Request");
+        else
+            DCMNET_INFO("Received N-EVENT-REPORT Request (MsgID " << eventReportReq.MessageID << ")");
+    }
+    else
+    {
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_INCOMING, NULL, presID));
+        DCMNET_ERROR("Expected N-EVENT-REPORT request but received DIMSE command 0x"
+                     << STD_NAMESPACE hex << STD_NAMESPACE setfill('0') << STD_NAMESPACE setw(4)
+                     << OFstatic_cast(unsigned int, request.CommandField));
+        delete statusDetail;
+        return DIMSE_BADCOMMANDTYPE;
+    }
+    if (statusDetail != NULL)
+    {
+        DCMNET_DEBUG("Request has status detail:" << OFendl << DcmObject::PrintHelper(*statusDetail));
+        delete statusDetail;
+    }
 
-  // Output dataset only if trace level is enabled
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_INCOMING, dataset, presID));
-  else
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_INCOMING, NULL, presID));
+    // Check if dataset is announced correctly
+    if (eventReportReq.DataSetType == DIMSE_DATASET_NULL)
+    {
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_INCOMING, NULL, presID));
+        DCMNET_ERROR("Received N-EVENT-REPORT request but no dataset announced, aborting");
+        return DIMSE_BADMESSAGE;
+    }
 
-  // Compare presentation context ID of command and data set
-  if (presIDdset != presID)
-  {
-    DCMNET_ERROR("Presentation Context ID of command (" << OFstatic_cast(unsigned int, presID)
-      << ") and data set (" << OFstatic_cast(unsigned int, presIDdset) << ") differ");
-    delete dataset;
-    return makeDcmnetCondition(DIMSEC_INVALIDPRESENTATIONCONTEXTID, OF_error,
-      "DIMSE: Presentation Contexts of Command and Data Set differ");
-  }
+    // Receive dataset
+    cond = receiveDIMSEDataset(&presIDdset, &dataset);
+    if (cond.bad())
+    {
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_INCOMING, NULL, presID));
+        return DIMSE_BADDATA;
+    }
 
-  // Check the request dataset and return the DIMSE status code to be used
-  statusCode = checkEVENTREPORTRequest(eventReportReq, dataset);
+    // Output dataset only if trace level is enabled
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::TRACE_LOG_LEVEL))
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_INCOMING, dataset, presID));
+    else
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, request, DIMSE_INCOMING, NULL, presID));
 
-  // Send back response
-  T_DIMSE_Message response;
-  // Make sure everything is zeroed (especially options)
-  bzero((char*)&response, sizeof(response));
+    // Compare presentation context ID of command and data set
+    if (presIDdset != presID)
+    {
+        DCMNET_ERROR("Presentation Context ID of command (" << OFstatic_cast(unsigned int, presID) << ") and data set ("
+                                                            << OFstatic_cast(unsigned int, presIDdset) << ") differ");
+        delete dataset;
+        return makeDcmnetCondition(DIMSEC_INVALIDPRESENTATIONCONTEXTID,
+                                   OF_error,
+                                   "DIMSE: Presentation Contexts of Command and Data Set differ");
+    }
 
-  T_DIMSE_N_EventReportRSP &eventReportRsp = response.msg.NEventReportRSP;
-  response.CommandField = DIMSE_N_EVENT_REPORT_RSP;
-  eventReportRsp.MessageIDBeingRespondedTo = eventReportReq.MessageID;
-  eventReportRsp.DimseStatus = statusCode;
-  eventReportRsp.DataSetType = DIMSE_DATASET_NULL;
-  eventReportRsp.opts = 0;
-  eventReportRsp.AffectedSOPClassUID[0] = 0;
-  eventReportRsp.AffectedSOPInstanceUID[0] = 0;
+    // Check the request dataset and return the DIMSE status code to be used
+    statusCode = checkEVENTREPORTRequest(eventReportReq, dataset);
 
-  if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
-  {
-    DCMNET_INFO("Sending N-EVENT-REPORT Response");
-    DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_OUTGOING, NULL, presID));
-  } else {
-    DCMNET_INFO("Sending N-EVENT-REPORT Response (" << DU_neventReportStatusString(statusCode) << ")");
-  }
-  cond = sendDIMSEMessage(presID, &response, NULL /*dataObject*/);
-  if (cond.bad())
-  {
-    DCMNET_ERROR("Failed sending N-EVENT-REPORT response: " << DimseCondition::dump(tempStr, cond));
-    delete dataset;
-    return cond;
-  }
+    // Send back response
+    T_DIMSE_Message response;
+    // Make sure everything is zeroed (especially options)
+    bzero((char*)&response, sizeof(response));
 
-  // Set return values
-  reqDataset = dataset;
-  eventTypeID = eventReportReq.EventTypeID;
+    T_DIMSE_N_EventReportRSP& eventReportRsp = response.msg.NEventReportRSP;
+    response.CommandField                    = DIMSE_N_EVENT_REPORT_RSP;
+    eventReportRsp.MessageIDBeingRespondedTo = eventReportReq.MessageID;
+    eventReportRsp.DimseStatus               = statusCode;
+    eventReportRsp.DataSetType               = DIMSE_DATASET_NULL;
+    eventReportRsp.opts                      = 0;
+    eventReportRsp.AffectedSOPClassUID[0]    = 0;
+    eventReportRsp.AffectedSOPInstanceUID[0] = 0;
 
-  return cond;
-}
+    if (DCM_dcmnetLogger.isEnabledFor(OFLogger::DEBUG_LOG_LEVEL))
+    {
+        DCMNET_INFO("Sending N-EVENT-REPORT Response");
+        DCMNET_DEBUG(DIMSE_dumpMessage(tempStr, response, DIMSE_OUTGOING, NULL, presID));
+    }
+    else
+    {
+        DCMNET_INFO("Sending N-EVENT-REPORT Response (" << DU_neventReportStatusString(statusCode) << ")");
+    }
+    cond = sendDIMSEMessage(presID, &response, NULL /*dataObject*/);
+    if (cond.bad())
+    {
+        DCMNET_ERROR("Failed sending N-EVENT-REPORT response: " << DimseCondition::dump(tempStr, cond));
+        delete dataset;
+        return cond;
+    }
 
+    // Set return values
+    reqDataset  = dataset;
+    eventTypeID = eventReportReq.EventTypeID;
+
+    return cond;
+}
 
-Uint16 DcmSCU::checkEVENTREPORTRequest(T_DIMSE_N_EventReportRQ & /*eventReportReq*/,
-                                       DcmDataset * /*reqDataset*/)
+Uint16 DcmSCU::checkEVENTREPORTRequest(T_DIMSE_N_EventReportRQ& /*eventReportReq*/, DcmDataset* /*reqDataset*/)
 {
-  // we default to success
-  return STATUS_Success;
+    // we default to success
+    return STATUS_Success;
 }
 
+OFCondition
+DcmSCU::handleSessionResponseDefault(const Uint16 dimseStatus, const OFString& message, OFBool& waitForNextResponse)
+{
+    waitForNextResponse = OFFalse;
+
+    // Do some basic validity checks
+    if (!isConnected())
+        return DIMSE_ILLEGALASSOCIATION;
+
+    if (DICOM_WARNING_STATUS(dimseStatus))
+    {
+        DCMNET_WARN("DIMSE status is: " << message);
+    }
+    else if (DICOM_PENDING_STATUS(dimseStatus))
+    {
+        waitForNextResponse = OFTrue;
+        DCMNET_DEBUG("DIMSE status is: " << message);
+    }
+    else if (dimseStatus == STATUS_Success)
+    {
+        DCMNET_DEBUG("DIMSE status is: " << message);
+    }
+    else
+    {
+        DCMNET_ERROR("DIMSE status is: " << message);
+    }
+
+    return EC_Normal;
+}
 
 /* ************************************************************************* */
 /*                         General message handling                          */
@@ -2142,41 +2115,53 @@ Uint16 DcmSCU::checkEVENTREPORTRequest(T_DIMSE_N_EventReportRQ & /*eventReportRe
 
 void DcmSCU::notifySENDProgress(const unsigned long byteCount)
 {
-  DCMNET_TRACE("Bytes sent: " << byteCount);
+    DCMNET_TRACE("Bytes sent: " << byteCount);
 }
 
-
 void DcmSCU::notifyRECEIVEProgress(const unsigned long byteCount)
 {
-  DCMNET_TRACE("Bytes received: " << byteCount);
+    DCMNET_TRACE("Bytes received: " << byteCount);
 }
 
-
 /* ************************************************************************* */
 /*                            Various helpers                                */
 /* ************************************************************************* */
 
 // Sends a DIMSE command and possibly also instance data to the configured peer DICOM application
 OFCondition DcmSCU::sendDIMSEMessage(const T_ASC_PresentationContextID presID,
-                                     T_DIMSE_Message *msg,
-                                     DcmDataset *dataObject,
-                                     DcmDataset **commandSet)
-{
-  if (!isConnected())
-    return DIMSE_ILLEGALASSOCIATION;
-  if (msg == NULL)
-    return DIMSE_NULLKEY;
-
-  OFCondition cond;
-  /* call the corresponding DIMSE function to send the message */
-  if (m_progressNotificationMode)
-  {
-    cond = DIMSE_sendMessageUsingMemoryData(m_assoc, presID, msg, NULL /*statusDetail*/, dataObject,
-                                            callbackSENDProgress, this /*callbackData*/, commandSet);
-  } else {
-    cond = DIMSE_sendMessageUsingMemoryData(m_assoc, presID, msg, NULL /*statusDetail*/, dataObject,
-                                            NULL /*callback*/, NULL /*callbackData*/, commandSet);
-  }
+                                     T_DIMSE_Message* msg,
+                                     DcmDataset* dataObject,
+                                     DcmDataset** commandSet)
+{
+    if (!isConnected())
+        return DIMSE_ILLEGALASSOCIATION;
+    if (msg == NULL)
+        return DIMSE_NULLKEY;
+
+    OFCondition cond;
+    /* call the corresponding DIMSE function to send the message */
+    if (m_progressNotificationMode)
+    {
+        cond = DIMSE_sendMessageUsingMemoryData(m_assoc,
+                                                presID,
+                                                msg,
+                                                NULL /*statusDetail*/,
+                                                dataObject,
+                                                callbackSENDProgress,
+                                                this /*callbackData*/,
+                                                commandSet);
+    }
+    else
+    {
+        cond = DIMSE_sendMessageUsingMemoryData(m_assoc,
+                                                presID,
+                                                msg,
+                                                NULL /*statusDetail*/,
+                                                dataObject,
+                                                NULL /*callback*/,
+                                                NULL /*callbackData*/,
+                                                commandSet);
+    }
 
 #if 0
   // currently disabled because it is not (yet) needed
@@ -2191,312 +2176,275 @@ OFCondition DcmSCU::sendDIMSEMessage(const T_ASC_PresentationContextID presID,
   }
 #endif
 
-  return cond;
+    return cond;
 }
 
-
 // Receive DIMSE command (excluding dataset!) over the currently open association
-OFCondition DcmSCU::receiveDIMSECommand(T_ASC_PresentationContextID *presID,
-                                        T_DIMSE_Message *msg,
-                                        DcmDataset **statusDetail,
-                                        DcmDataset **commandSet,
+OFCondition DcmSCU::receiveDIMSECommand(T_ASC_PresentationContextIDpresID,
+                                        T_DIMSE_Messagemsg,
+                                        DcmDataset** statusDetail,
+                                        DcmDataset** commandSet,
                                         const Uint32 timeout)
 {
-  if (!isConnected())
-    return DIMSE_ILLEGALASSOCIATION;
+    if (!isConnected())
+        return DIMSE_ILLEGALASSOCIATION;
 
-  OFCondition cond;
-  if (timeout > 0)
-  {
-    /* call the corresponding DIMSE function to receive the command (use specified timeout)*/
-    cond = DIMSE_receiveCommand(m_assoc, DIMSE_NONBLOCKING, timeout, presID,
-                                msg, statusDetail, commandSet);
-  } else {
-    /* call the corresponding DIMSE function to receive the command (use default timeout) */
-    cond = DIMSE_receiveCommand(m_assoc, m_blockMode, m_dimseTimeout, presID,
-                                msg, statusDetail, commandSet);
-  }
-  return cond;
+    OFCondition cond;
+    if (timeout > 0)
+    {
+        /* call the corresponding DIMSE function to receive the command (use specified timeout)*/
+        cond = DIMSE_receiveCommand(m_assoc, DIMSE_NONBLOCKING, timeout, presID, msg, statusDetail, commandSet);
+    }
+    else
+    {
+        /* call the corresponding DIMSE function to receive the command (use default timeout) */
+        cond = DIMSE_receiveCommand(m_assoc, m_blockMode, m_dimseTimeout, presID, msg, statusDetail, commandSet);
+    }
+    return cond;
 }
 
 // Receives one dataset (of instance data) via network from another DICOM application
-OFCondition DcmSCU::receiveDIMSEDataset(T_ASC_PresentationContextID *presID,
-                                        DcmDataset **dataObject)
+OFCondition DcmSCU::receiveDIMSEDataset(T_ASC_PresentationContextID* presID, DcmDataset** dataObject)
 {
-  if (!isConnected())
-    return DIMSE_ILLEGALASSOCIATION;
+    if (!isConnected())
+        return DIMSE_ILLEGALASSOCIATION;
 
-  OFCondition cond;
-  /* call the corresponding DIMSE function to receive the dataset */
-  if (m_progressNotificationMode)
-  {
-    cond = DIMSE_receiveDataSetInMemory(m_assoc, m_blockMode, m_dimseTimeout, presID, dataObject,
-                                        callbackRECEIVEProgress, this /*callbackData*/);
-  } else {
-    cond = DIMSE_receiveDataSetInMemory(m_assoc, m_blockMode, m_dimseTimeout, presID, dataObject,
-                                        NULL /*callback*/, NULL /*callbackData*/);
-  }
+    OFCondition cond;
+    /* call the corresponding DIMSE function to receive the dataset */
+    if (m_progressNotificationMode)
+    {
+        cond = DIMSE_receiveDataSetInMemory(
+            m_assoc, m_blockMode, m_dimseTimeout, presID, dataObject, callbackRECEIVEProgress, this /*callbackData*/);
+    }
+    else
+    {
+        cond = DIMSE_receiveDataSetInMemory(
+            m_assoc, m_blockMode, m_dimseTimeout, presID, dataObject, NULL /*callback*/, NULL /*callbackData*/);
+    }
 
-  if (cond.good())
-  {
-    DCMNET_DEBUG("Received dataset on presentation context " << OFstatic_cast(unsigned int, *presID));
-  }
-  else
-  {
-    OFString tempStr;
-    DCMNET_ERROR("Unable to receive dataset on presentation context "
-      << OFstatic_cast(unsigned int, *presID) << ": " << DimseCondition::dump(tempStr, cond));
-  }
-  return cond;
+    if (cond.good())
+    {
+        DCMNET_DEBUG("Received dataset on presentation context " << OFstatic_cast(unsigned int, *presID));
+    }
+    else
+    {
+        OFString tempStr;
+        DCMNET_ERROR("Unable to receive dataset on presentation context "
+                     << OFstatic_cast(unsigned int, *presID) << ": " << DimseCondition::dump(tempStr, cond));
+    }
+    return cond;
 }
 
-
 void DcmSCU::setMaxReceivePDULength(const Uint32 maxRecPDU)
 {
-  m_maxReceivePDULength = maxRecPDU;
+    m_maxReceivePDULength = maxRecPDU;
 }
 
-
 void DcmSCU::setDIMSEBlockingMode(const T_DIMSE_BlockingMode blockingMode)
 {
-  m_blockMode = blockingMode;
+    m_blockMode = blockingMode;
 }
 
-
-void DcmSCU::setAETitle(const OFString &myAETtitle)
+void DcmSCU::setAETitle(const OFString& myAETtitle)
 {
-  m_ourAETitle = myAETtitle;
+    m_ourAETitle = myAETtitle;
 }
 
-
-void DcmSCU::setPeerHostName(const OFString &peerHostName)
+void DcmSCU::setPeerHostName(const OFString& peerHostName)
 {
-  m_peer = peerHostName;
+    m_peer = peerHostName;
 }
 
-
-void DcmSCU::setPeerAETitle(const OFString &peerAETitle)
+void DcmSCU::setPeerAETitle(const OFString& peerAETitle)
 {
-  m_peerAETitle = peerAETitle;
+    m_peerAETitle = peerAETitle;
 }
 
-
 void DcmSCU::setPeerPort(const Uint16 peerPort)
 {
-  m_peerPort = peerPort;
+    m_peerPort = peerPort;
 }
 
-
 void DcmSCU::setDIMSETimeout(const Uint32 dimseTimeout)
 {
-  m_dimseTimeout = dimseTimeout;
+    m_dimseTimeout = dimseTimeout;
 }
 
-
 void DcmSCU::setACSETimeout(const Uint32 acseTimeout)
 {
-  m_acseTimeout = acseTimeout;
+    m_acseTimeout = acseTimeout;
 }
 
-
 void DcmSCU::setConnectionTimeout(const Sint32 connectionTimeout)
 {
-  dcmConnectionTimeout.set(connectionTimeout);
+    dcmConnectionTimeout.set(connectionTimeout);
 }
 
-
-void DcmSCU::setAssocConfigFileAndProfile(const OFString &filename,
-                                          const OFString &profile)
+void DcmSCU::setAssocConfigFileAndProfile(const OFString& filename, const OFString& profile)
 {
-  m_assocConfigFilename = filename;
-  m_assocConfigProfile = profile;
+    m_assocConfigFilename = filename;
+    m_assocConfigProfile  = profile;
 }
 
-
 void DcmSCU::setStorageDir(const OFString& storeDir)
 {
-  m_storageDir = storeDir;
+    m_storageDir = storeDir;
 }
 
-
 void DcmSCU::setStorageMode(const DcmStorageMode storageMode)
 {
-  m_storageMode = storageMode;
+    m_storageMode = storageMode;
 }
 
-
 void DcmSCU::setVerbosePCMode(const OFBool mode)
 {
-  m_verbosePCMode = mode;
+    m_verbosePCMode = mode;
 }
 
-
 void DcmSCU::setDatasetConversionMode(const OFBool mode)
 {
-  m_datasetConversionMode = mode;
+    m_datasetConversionMode = mode;
 }
 
-
 void DcmSCU::setProgressNotificationMode(const OFBool mode)
 {
-  m_progressNotificationMode = mode;
+    m_progressNotificationMode = mode;
 }
 
-
 /* Get methods */
 
 OFBool DcmSCU::isConnected() const
 {
-  return (m_assoc != NULL) && (m_assoc->DULassociation != NULL);
+    return (m_assoc != NULL) && (m_assoc->DULassociation != NULL);
 }
 
 Uint32 DcmSCU::getMaxReceivePDULength() const
 {
-  return m_maxReceivePDULength;
+    return m_maxReceivePDULength;
 }
 
-
 OFBool DcmSCU::getTLSEnabled() const
 {
-  return OFFalse;
+    return OFFalse;
 }
 
-
 T_DIMSE_BlockingMode DcmSCU::getDIMSEBlockingMode() const
 {
-  return m_blockMode;
+    return m_blockMode;
 }
 
-
-const OFString &DcmSCU::getAETitle() const
+const OFString& DcmSCU::getAETitle() const
 {
-  return m_ourAETitle;
+    return m_ourAETitle;
 }
 
-
-const OFString &DcmSCU::getPeerHostName() const
+const OFString& DcmSCU::getPeerHostName() const
 {
-  return m_peer;
+    return m_peer;
 }
 
-
-const OFString &DcmSCU::getPeerAETitle() const
+const OFString& DcmSCU::getPeerAETitle() const
 {
-  return m_peerAETitle;
+    return m_peerAETitle;
 }
 
-
 Uint16 DcmSCU::getPeerPort() const
 {
-  return m_peerPort;
+    return m_peerPort;
 }
 
-
 Uint32 DcmSCU::getDIMSETimeout() const
 {
-  return m_dimseTimeout;
+    return m_dimseTimeout;
 }
 
-
 Uint32 DcmSCU::getACSETimeout() const
 {
-  return m_acseTimeout;
+    return m_acseTimeout;
 }
 
-
 Sint32 DcmSCU::getConnectionTimeout() const
 {
-  return dcmConnectionTimeout.get();
+    return dcmConnectionTimeout.get();
 }
 
-
 OFString DcmSCU::getStorageDir() const
 {
-  return m_storageDir;
+    return m_storageDir;
 }
 
-
 DcmStorageMode DcmSCU::getStorageMode() const
 {
-  return m_storageMode;
+    return m_storageMode;
 }
 
-
 OFBool DcmSCU::getVerbosePCMode() const
 {
-  return m_verbosePCMode;
+    return m_verbosePCMode;
 }
 
-
 OFBool DcmSCU::getDatasetConversionMode() const
 {
-  return m_datasetConversionMode;
+    return m_datasetConversionMode;
 }
 
-
 OFBool DcmSCU::getProgressNotificationMode() const
 {
-  return m_progressNotificationMode;
+    return m_progressNotificationMode;
 }
 
-
-OFCondition DcmSCU::getDatasetInfo(DcmDataset *dataset,
-                                   OFString &sopClassUID,
-                                   OFString &sopInstanceUID,
-                                   E_TransferSyntax &transferSyntax)
+OFCondition DcmSCU::getDatasetInfo(DcmDataset* dataset,
+                                   OFString& sopClassUID,
+                                   OFString& sopInstanceUID,
+                                   E_TransferSyntax& transferSyntax)
 {
-  OFCondition status = EC_IllegalParameter;
-  sopClassUID.clear();
-  sopInstanceUID.clear();
-  transferSyntax = EXS_Unknown;
-  if (dataset != NULL)
-  {
-    // ignore returned condition codes (e.g. EC_TagNotFound)
-    dataset->findAndGetOFString(DCM_SOPClassUID, sopClassUID);
-    dataset->findAndGetOFString(DCM_SOPInstanceUID, sopInstanceUID);
-    transferSyntax = dataset->getOriginalXfer();
-    // check return values for validity
-    if (sopClassUID.empty())
-      status = NET_EC_InvalidSOPClassUID;
-    else if (sopInstanceUID.empty())
-      status = NET_EC_InvalidSOPInstanceUID;
-    else if (transferSyntax == EXS_Unknown)
-      status = NET_EC_UnknownTransferSyntax;
-    else
-      status = EC_Normal;
-  }
-  return status;
+    OFCondition status = EC_IllegalParameter;
+    sopClassUID.clear();
+    sopInstanceUID.clear();
+    transferSyntax = EXS_Unknown;
+    if (dataset != NULL)
+    {
+        // ignore returned condition codes (e.g. EC_TagNotFound)
+        dataset->findAndGetOFString(DCM_SOPClassUID, sopClassUID);
+        dataset->findAndGetOFString(DCM_SOPInstanceUID, sopInstanceUID);
+        transferSyntax = dataset->getOriginalXfer();
+        // check return values for validity
+        if (sopClassUID.empty())
+            status = NET_EC_InvalidSOPClassUID;
+        else if (sopInstanceUID.empty())
+            status = NET_EC_InvalidSOPInstanceUID;
+        else if (transferSyntax == EXS_Unknown)
+            status = NET_EC_UnknownTransferSyntax;
+        else
+            status = EC_Normal;
+    }
+    return status;
 }
 
-
 /* ************************************************************************* */
 /*                            Callback functions                             */
 /* ************************************************************************* */
 
-void DcmSCU::callbackSENDProgress(void *callbackContext,
-                                  const unsigned long byteCount)
+void DcmSCU::callbackSENDProgress(void* callbackContext, const unsigned long byteCount)
 {
-  if (callbackContext != NULL)
-    OFreinterpret_cast(DcmSCU *, callbackContext)->notifySENDProgress(byteCount);
+    if (callbackContext != NULL)
+        OFreinterpret_cast(DcmSCU*, callbackContext)->notifySENDProgress(byteCount);
 }
 
-
-void DcmSCU::callbackRECEIVEProgress(void *callbackContext,
-                                     const unsigned long byteCount)
+void DcmSCU::callbackRECEIVEProgress(void* callbackContext, const unsigned long byteCount)
 {
-  if (callbackContext != NULL)
-    OFreinterpret_cast(DcmSCU *, callbackContext)->notifyRECEIVEProgress(byteCount);
+    if (callbackContext != NULL)
+        OFreinterpret_cast(DcmSCU*, callbackContext)->notifyRECEIVEProgress(byteCount);
 }
 
-
 /* ************************************************************************* */
 /*                          class RetrieveResponse                           */
 /* ************************************************************************* */
 
 void RetrieveResponse::print()
 {
-  DCMNET_INFO("  Number of Remaining Suboperations : " << m_numberOfRemainingSubops);
-  DCMNET_INFO("  Number of Completed Suboperations : " << m_numberOfCompletedSubops);
-  DCMNET_INFO("  Number of Failed Suboperations    : " << m_numberOfFailedSubops);
-  DCMNET_INFO("  Number of Warning Suboperations   : " << m_numberOfWarningSubops);
+    DCMNET_INFO("  Number of Remaining Suboperations : " << m_numberOfRemainingSubops);
+    DCMNET_INFO("  Number of Completed Suboperations : " << m_numberOfCompletedSubops);
+    DCMNET_INFO("  Number of Failed Suboperations    : " << m_numberOfFailedSubops);
+    DCMNET_INFO("  Number of Warning Suboperations   : " << m_numberOfWarningSubops);
 }
index 2044aa1e150d6a7fb6b3f56e093c9bc958c84311..b8c0ab5a8340ad0dac27a70eed6b42e0a910feac 100644 (file)
@@ -1,5 +1,5 @@
 # declare executables
-DCMTK_ADD_EXECUTABLE(dcmnet_tests tests tdump tpool tscuscp)
+DCMTK_ADD_EXECUTABLE(dcmnet_tests tests tdump tdimse tpool tscuscp tscusession)
 
 # make sure executables are linked to the corresponding libraries
 DCMTK_TARGET_LINK_MODULES(dcmnet_tests dcmnet)
index 5a521d91c3ed05758035da8cd8ae7bf947bb4311..172d63bfbf54f05f68486f06bb215f79cbcf590b 100644 (file)
@@ -247,12 +247,12 @@ tpool.o: tpool.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofbmanip.h ../include/dcmtk/dcmnet/lst.h \
  ../include/dcmtk/dcmnet/dul.h ../include/dcmtk/dcmnet/extneg.h \
  ../include/dcmtk/dcmnet/dcuserid.h ../include/dcmtk/dcmnet/dntypes.h \
- ../include/dcmtk/dcmnet/dimse.h ../include/dcmtk/dcmnet/scpcfg.h \
- ../include/dcmtk/dcmnet/dcasccff.h ../include/dcmtk/dcmnet/dcasccfg.h \
- ../include/dcmtk/dcmnet/dccftsmp.h ../include/dcmtk/dcmnet/dccfuidh.h \
- ../include/dcmtk/dcmnet/dccfpcmp.h ../include/dcmtk/dcmnet/dccfrsmp.h \
- ../include/dcmtk/dcmnet/dccfenmp.h ../include/dcmtk/dcmnet/dccfprmp.h \
- ../include/dcmtk/dcmnet/diutil.h ../include/dcmtk/dcmnet/scu.h
+ ../include/dcmtk/dcmnet/dimse.h ../include/dcmtk/dcmnet/diutil.h \
+ ../include/dcmtk/dcmnet/scpcfg.h ../include/dcmtk/dcmnet/dcasccff.h \
+ ../include/dcmtk/dcmnet/dcasccfg.h ../include/dcmtk/dcmnet/dccftsmp.h \
+ ../include/dcmtk/dcmnet/dccfuidh.h ../include/dcmtk/dcmnet/dccfpcmp.h \
+ ../include/dcmtk/dcmnet/dccfrsmp.h ../include/dcmtk/dcmnet/dccfenmp.h \
+ ../include/dcmtk/dcmnet/dccfprmp.h ../include/dcmtk/dcmnet/scu.h
 tscuscp.o: tscuscp.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../ofstd/include/dcmtk/ofstd/oftest.h \
@@ -380,9 +380,143 @@ tscuscp.o: tscuscp.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofbmanip.h ../include/dcmtk/dcmnet/lst.h \
  ../include/dcmtk/dcmnet/dul.h ../include/dcmtk/dcmnet/extneg.h \
  ../include/dcmtk/dcmnet/dcuserid.h ../include/dcmtk/dcmnet/dntypes.h \
- ../include/dcmtk/dcmnet/dimse.h ../include/dcmtk/dcmnet/scpcfg.h \
- ../include/dcmtk/dcmnet/dcasccff.h ../include/dcmtk/dcmnet/dcasccfg.h \
- ../include/dcmtk/dcmnet/dccftsmp.h ../include/dcmtk/dcmnet/dccfuidh.h \
- ../include/dcmtk/dcmnet/dccfpcmp.h ../include/dcmtk/dcmnet/dccfrsmp.h \
- ../include/dcmtk/dcmnet/dccfenmp.h ../include/dcmtk/dcmnet/dccfprmp.h \
- ../include/dcmtk/dcmnet/diutil.h ../include/dcmtk/dcmnet/scu.h
+ ../include/dcmtk/dcmnet/dimse.h ../include/dcmtk/dcmnet/diutil.h \
+ ../include/dcmtk/dcmnet/scpcfg.h ../include/dcmtk/dcmnet/dcasccff.h \
+ ../include/dcmtk/dcmnet/dcasccfg.h ../include/dcmtk/dcmnet/dccftsmp.h \
+ ../include/dcmtk/dcmnet/dccfuidh.h ../include/dcmtk/dcmnet/dccfpcmp.h \
+ ../include/dcmtk/dcmnet/dccfrsmp.h ../include/dcmtk/dcmnet/dccfenmp.h \
+ ../include/dcmtk/dcmnet/dccfprmp.h ../include/dcmtk/dcmnet/scu.h
+tscusession.o: tscusession.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmnet/scp.h ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../include/dcmtk/dcmnet/assoc.h ../include/dcmtk/dcmnet/dicom.h \
+ ../include/dcmtk/dcmnet/cond.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../include/dcmtk/dcmnet/dndefine.h ../include/dcmtk/dcmnet/dcompat.h \
+ ../../ofstd/include/dcmtk/ofstd/ofbmanip.h ../include/dcmtk/dcmnet/lst.h \
+ ../include/dcmtk/dcmnet/dul.h ../include/dcmtk/dcmnet/extneg.h \
+ ../include/dcmtk/dcmnet/dcuserid.h ../include/dcmtk/dcmnet/dntypes.h \
+ ../include/dcmtk/dcmnet/dimse.h ../include/dcmtk/dcmnet/diutil.h \
+ ../include/dcmtk/dcmnet/scpcfg.h ../include/dcmtk/dcmnet/dcasccff.h \
+ ../include/dcmtk/dcmnet/dcasccfg.h ../include/dcmtk/dcmnet/dccftsmp.h \
+ ../include/dcmtk/dcmnet/dccfuidh.h ../include/dcmtk/dcmnet/dccfpcmp.h \
+ ../include/dcmtk/dcmnet/dccfrsmp.h ../include/dcmtk/dcmnet/dccfenmp.h \
+ ../include/dcmtk/dcmnet/dccfprmp.h ../include/dcmtk/dcmnet/scu.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h \
+ ../../ofstd/include/dcmtk/ofstd/oftimer.h
index c12b3af42fc3e1269cc21c5e5414349cfdcc7cd7..2d87c9cfcecf7e5c12dd8a0c751b651b9a304289 100644 (file)
@@ -23,7 +23,7 @@ LIBDIRS = -L$(top_srcdir)/libsrc -L$(ofstddir)/libsrc -L$(oflogdir)/libsrc \
 LOCALLIBS = -ldcmnet -ldcmdata -loflog -lofstd $(ZLIBLIBS) $(TCPWRAPPERLIBS) \
        $(CHARCONVLIBS) $(MATHLIBS)
 
-objs = tests.o tdump.o tpool.o tscuscp.o
+objs = tests.o tdump.o tdimse.o tpool.o tscuscp.o tscusession.o
 progs = tests
 
 
diff --git a/dcmnet/tests/tdimse.cc b/dcmnet/tests/tdimse.cc
new file mode 100644 (file)
index 0000000..512f887
--- /dev/null
@@ -0,0 +1,89 @@
+/*
+ *
+ *  Copyright (C) 2020, J. Riesmeier, Oldenburg, Germany
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmnet
+ *
+ *  Author:  Joerg Riesmeier
+ *
+ *  Purpose: test program for DIMSE Status Codes and Classes
+ *
+ */
+
+
+#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
+
+#include "dcmtk/ofstd/oftest.h"
+#include "dcmtk/dcmnet/dimse.h"
+
+
+OFTEST(dcmnet_dimseStatusClass)
+{
+    // success
+    OFCHECK( DICOM_SUCCESS_STATUS(0x0000));
+    OFCHECK(!DICOM_SUCCESS_STATUS(0xabce));
+    // failure
+    OFCHECK( DICOM_FAILURE_STATUS(0xa000));
+    OFCHECK( DICOM_FAILURE_STATUS(0xa001));
+    OFCHECK( DICOM_FAILURE_STATUS(0xabcd));
+    OFCHECK(!DICOM_FAILURE_STATUS(0xb000));
+    OFCHECK(!DICOM_FAILURE_STATUS(0xbeaf));
+    OFCHECK( DICOM_FAILURE_STATUS(0xc000));
+    OFCHECK( DICOM_FAILURE_STATUS(0xc0c0));
+    OFCHECK( DICOM_FAILURE_STATUS(0xcfff));
+    OFCHECK(!DICOM_FAILURE_STATUS(0xd000));
+    OFCHECK(!DICOM_FAILURE_STATUS(0xd00f));
+    OFCHECK( DICOM_FAILURE_STATUS(0x0100));
+    OFCHECK(!DICOM_FAILURE_STATUS(0x0107));
+    OFCHECK( DICOM_FAILURE_STATUS(0x0108));
+    OFCHECK(!DICOM_FAILURE_STATUS(0x0116));
+    OFCHECK( DICOM_FAILURE_STATUS(0x0117));
+    OFCHECK( DICOM_FAILURE_STATUS(0x01ff));
+    OFCHECK( DICOM_FAILURE_STATUS(0x0200));
+    OFCHECK( DICOM_FAILURE_STATUS(0x0222));
+    OFCHECK( DICOM_FAILURE_STATUS(0x02ff));
+    OFCHECK(!DICOM_FAILURE_STATUS(0x0300));
+    OFCHECK(!DICOM_FAILURE_STATUS(0x2200));
+    // warning
+    OFCHECK(!DICOM_WARNING_STATUS(0x0000));
+    OFCHECK( DICOM_WARNING_STATUS(0x0001));
+    OFCHECK(!DICOM_WARNING_STATUS(0x0002));
+    OFCHECK( DICOM_WARNING_STATUS(0x0107));
+    OFCHECK(!DICOM_WARNING_STATUS(0x0108));
+    OFCHECK( DICOM_WARNING_STATUS(0x0116));
+    OFCHECK(!DICOM_WARNING_STATUS(0x0117));
+    OFCHECK( DICOM_WARNING_STATUS(0xb000));
+    OFCHECK( DICOM_WARNING_STATUS(0xb001));
+    OFCHECK( DICOM_WARNING_STATUS(0xbfff));
+    OFCHECK(!DICOM_WARNING_STATUS(0xc000));
+    // cancel
+    OFCHECK( DICOM_CANCEL_STATUS (0xfe00));
+    OFCHECK(!DICOM_CANCEL_STATUS (0xfe01));
+    OFCHECK(!DICOM_CANCEL_STATUS (0xfefe));
+    // pending
+    OFCHECK( DICOM_PENDING_STATUS(0xff00));
+    OFCHECK( DICOM_PENDING_STATUS(0xff01));
+    OFCHECK(!DICOM_PENDING_STATUS(0xff02));
+    OFCHECK(!DICOM_PENDING_STATUS(0xffff));
+    // any of the standard codes
+    OFCHECK( DICOM_STANDARD_STATUS(0x0000));
+    OFCHECK( DICOM_STANDARD_STATUS(0x0001));
+    OFCHECK( DICOM_STANDARD_STATUS(0x0111));
+    OFCHECK( DICOM_STANDARD_STATUS(0x0222));
+    OFCHECK(!DICOM_STANDARD_STATUS(0x0300));
+    OFCHECK(!DICOM_STANDARD_STATUS(0x9999));
+    OFCHECK( DICOM_STANDARD_STATUS(0xabcd));
+    OFCHECK( DICOM_STANDARD_STATUS(0xbcde));
+    OFCHECK( DICOM_STANDARD_STATUS(0xc0de));
+    OFCHECK(!DICOM_STANDARD_STATUS(0xdead));
+    OFCHECK(!DICOM_STANDARD_STATUS(0xffff));
+}
index ed675f09c5c5b639d36a8a20ebcb92ca01d0efbc..4e0dd0d34af6ed2f1a0b3d7046dead20ac17275c 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2009-2015, OFFIS e.V.
+ *  Copyright (C) 2009-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #include "dcmtk/ofstd/oftest.h"
 #include "dcmtk/dcmdata/dcvrui.h"
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmdata/dcdict.h"
 #include "dcmtk/dcmnet/dimse.h"
 
 
 OFTEST(dcmnet_dimseDump_nullByte)
 {
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
     const char expected[] = "===================== INCOMING DIMSE MESSAGE ====================\nMessage Type                  : C-ECHO RQ\nMessage ID                    : 42\nData Set                      : present\n-----------------------------------------------------------------(fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n(0000,1000) UI [1.2\0]                                   #   4, 1 AffectedSOPInstanceUID\n(fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n======================= END DIMSE MESSAGE =======================";
     OFString result;
     T_DIMSE_C_EchoRQ rq = { 42, "1.2.3\0", DIMSE_DATASET_PRESENT };
index a20e2f0708dfa760e760326f90e4cc35f4817adc..c84a701fed304640994dd6adab2dc60d434f481f 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2012-2017, OFFIS e.V.
+ *  Copyright (C) 2012-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -24,6 +24,7 @@
 #include "dcmtk/ofstd/oftest.h"
 
 OFTEST_REGISTER(dcmnet_dimseDump_nullByte);
+OFTEST_REGISTER(dcmnet_dimseStatusClass);
 
 #ifdef WITH_THREADS
 OFTEST_REGISTER(dcmnet_scp_pool);
@@ -36,6 +37,7 @@ OFTEST_REGISTER(dcmnet_scp_no_stop_wo_request_noblock);
 OFTEST_REGISTER(dcmnet_scp_no_stop_wo_request_block);
 OFTEST_REGISTER(dcmnet_scp_no_term_notify_without_association);
 OFTEST_REGISTER(dcmnet_scp_role_selection);
+OFTEST_REGISTER(dcmnet_scu_session_handler);
 #endif // WITH_THREADS
 
 OFTEST_MAIN("dcmnet")
diff --git a/dcmnet/tests/tscusession.cc b/dcmnet/tests/tscusession.cc
new file mode 100644 (file)
index 0000000..7ae4ff5
--- /dev/null
@@ -0,0 +1,349 @@
+/*
+ *
+ *  Copyright (C) 2019-2020, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    Open Connections GmbH
+ *    Stau 33
+ *    D-26122 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmnet
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Test DcmSCU's C-FIND/GET/MOVE session handling
+ *
+ */
+
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+
+#ifdef WITH_THREADS
+
+#define INCLUDE_CMATH
+#include "dcmtk/dcmnet/scp.h"
+#include "dcmtk/dcmnet/scu.h"
+#include "dcmtk/ofstd/ofstdinc.h"
+#include "dcmtk/ofstd/oftest.h"
+#include "dcmtk/ofstd/oftimer.h"
+
+static Uint8 NUM_DIMSE_REQUESTS = 5;
+
+/** Method that ensures that the current thread is actually sleeping for the
+ *  defined number of seconds (at least).
+ *  @param sleep The number of seconds to sleep (at least)
+ */
+static void force_sleep(Uint32 sleep)
+{
+    OFTimer timer;
+    double elapsed = timer.getDiff();
+    while (elapsed < (double)sleep)
+    {
+        // Use ceiling since otherwise we could wait too short
+        OFStandard::sleep(OFstatic_cast(unsigned int, ceil(sleep - elapsed)));
+        elapsed = timer.getDiff();
+    }
+}
+
+/** SCP derived from DcmSCP that has simple handlers for MOVE, GET and FIND
+ *  and allows stopping after one association.
+ */
+struct SessionSCP : public DcmSCP, OFThread
+{
+
+    /** Constructor
+     */
+    SessionSCP()
+        : DcmSCP()
+    {
+    }
+
+    /** Overwrite method from DcmSCP in order to stop after one association.
+     *  @return Returns OFTrue (stop after first association)
+     */
+    virtual OFBool stopAfterCurrentAssociation()
+    {
+        return OFTrue;
+    }
+
+    /** Overwrite DcmSCP method to enable handling of C-FIND and C-MOVE messages (TODO: C-GET)
+     *  @param  incomingMsg Incoming DIMSE message
+     *  @param  presInfo Presentation Context information
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition handleIncomingCommand(T_DIMSE_Message* incomingMsg, const DcmPresentationContextInfo& presInfo)
+    {
+        OFCondition result;
+        DcmDataset* dset = NULL;
+        if (incomingMsg->CommandField == DIMSE_C_FIND_RQ)
+        {
+            // Call our custom FIND handler
+            result = handleFIND(incomingMsg->msg.CFindRQ, presInfo.presentationContextID, dset);
+        }
+        else if (incomingMsg->CommandField == DIMSE_C_MOVE_RQ)
+        {
+            // Call our custom MOVE handler
+            OFString dest = incomingMsg->msg.CMoveRQ.MoveDestination;
+            result        = handleMOVE(incomingMsg->msg.CMoveRQ, presInfo.presentationContextID, dset, dest);
+        }
+        else
+            result = DcmSCP::handleIncomingCommand(incomingMsg, presInfo);
+
+        delete dset;
+        return result;
+    }
+
+    /** Overwrite DcmSCP method to to add specific C-MOVE handler. Sends NUM_DIMSE_REQUESTS
+     *  DIMSE responses back, all in status PENDING, last in status SUCCESS.
+     *  @param  reqMessage Incoming DIMSE message
+     *  @param  presID Presentation Context ID
+     *  @param  reqDataset Request dataset
+     *  @param  moveDest Move Destination AE Title
+     *  @return EC_Normal if successful, error otherwise
+     */
+    OFCondition handleMOVE(T_DIMSE_C_MoveRQ& reqMessage,
+                           const T_ASC_PresentationContextID presID,
+                           DcmDataset*& reqDataset,
+                           OFString& moveDest)
+    {
+        OFCondition result = DcmSCP::receiveMOVERequest(reqMessage, presID, reqDataset, moveDest);
+        if (result.good())
+        {
+            OFString sop_class, ts;
+            OFunique_ptr<DcmDataset> rsp(new DcmDataset);
+            *rsp = *reqDataset;
+            DcmSCP::findPresentationContext(presID, sop_class, ts);
+            Uint16 status = STATUS_MOVE_Pending_SubOperationsAreContinuing;
+            // Send back configured number of responses, all but last with status PENDING (last: SUCCESS).
+            // All but the last one will return a copy of the request dataset (random choice for this test;
+            // last response will not have a dataset.
+            for (Uint8 n = 1; n <= NUM_DIMSE_REQUESTS; n++)
+            {
+                if (n == NUM_DIMSE_REQUESTS)
+                {
+                    rsp.reset(NULL);
+                    status = STATUS_Success;
+                }
+                result = DcmSCP::sendMOVEResponse(
+                    presID, reqMessage.MessageID, sop_class, rsp.get(), status, NULL, NUM_DIMSE_REQUESTS - n, n, 0, 0);
+            }
+        }
+        return result;
+    }
+
+    /** Overwrite DcmSCP method to to add specific C-FIND handler. Sends NUM_DIMSE_REQUESTS
+     *  DIMSE responses back, all in status PENDING, last in status SUCCESS.
+     *  @param  reqMessage Incoming DIMSE message
+     *  @param  presID Presentation Context ID
+     *  @param  reqDataset Request dataset
+     *  @return EC_Normal if successful, error otherwise
+     */
+    OFCondition
+    handleFIND(T_DIMSE_C_FindRQ& reqMessage, const T_ASC_PresentationContextID presID, DcmDataset*& reqDataset)
+    {
+        OFCondition result = DcmSCP::receiveFINDRequest(reqMessage, presID, reqDataset);
+        if (result.good())
+        {
+            OFString sop_class, ts;
+            OFunique_ptr<DcmDataset> rsp(new DcmDataset);
+            *rsp = *reqDataset;
+            DcmSCP::findPresentationContext(presID, sop_class, ts);
+            Uint16 status = STATUS_FIND_Pending_MatchesAreContinuing;
+            // Send back configured number of responses, all but last with status PENDING (last: SUCCESS).
+            // All but the last one will return a copy of the request dataset (random choice for this test;
+            // last response will not have a dataset.
+            for (Uint8 n = 1; n <= NUM_DIMSE_REQUESTS; n++)
+            {
+                if (n == NUM_DIMSE_REQUESTS)
+                {
+                    rsp.reset(NULL);
+                    status = STATUS_Success;
+                }
+                result = DcmSCP::sendFINDResponse(presID, reqMessage.MessageID, sop_class, rsp.get(), status, NULL);
+            }
+        }
+        return result;
+    }
+
+    /** Method called by OFThread to start SCP operation. Starts listen() loop of DcmSCP.
+     */
+    virtual void run()
+    {
+        listen();
+    }
+};
+
+/** Class derived from DcmSCU that has support for C-FIND/MOVE and GET-related
+ *  SOP Classes. Also it has handlers for those DIMSE messages call the original
+ *  handlers from DcmSCU and simply count how often they are called.
+ *  The goal is to exercise the internal default response handing built into
+ *  DcmSCU for handling C-FIND/MOVE and GET-related "sessions".
+ */
+struct SessionSCU : public DcmSCU
+{
+    /** Constructor
+     */
+    SessionSCU()
+        : m_session_counter(0)
+    {
+        OFList<OFString> ts;
+        ts.push_back(UID_LittleEndianImplicitTransferSyntax);
+        OFCHECK(addPresentationContext(UID_FINDPatientRootQueryRetrieveInformationModel, ts).good());
+        OFCHECK(addPresentationContext(UID_MOVEPatientRootQueryRetrieveInformationModel, ts).good());
+        OFCHECK(addPresentationContext(UID_GETPatientRootQueryRetrieveInformationModel, ts).good());
+    }
+
+    /** Overwrites method from DcmSCU.
+     *  Handles incoming C-GET response. Just counts number of calls and then forwards
+     *  handling to default DcmSCU handler.
+     *  @param  presID Presentation Context ID
+     *  @param  response The C-GET response received
+     *  @param  continueCGETSession Will receive information whether it should be waited
+     *          for further C-GET responses.
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition handleCGETResponse(const T_ASC_PresentationContextID presID,
+                                           RetrieveResponse* response,
+                                           OFBool& continueCGETSession)
+    {
+        m_session_counter++;
+        return DcmSCU::handleCGETResponse(presID, response, continueCGETSession);
+    }
+
+    /** Overwrites method from DcmSCU.
+     *  Handles incoming C-MOVE response. Just counts number of calls and then forwards
+     *  handling to default DcmSCU handler.
+     *  @param  presID Presentation Context ID
+     *  @param  response The C-MOVE response received
+     *  @param  waitForNextResponse Will receive information whether it should be waited
+     *          for further C-MOVE responses.
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition handleMOVEResponse(const T_ASC_PresentationContextID presID,
+                                           RetrieveResponse* response,
+                                           OFBool& waitForNextResponse)
+    {
+        m_session_counter++;
+        return DcmSCU::handleMOVEResponse(presID, response, waitForNextResponse);
+    }
+
+    /** Overwrites method from DcmSCU.
+     *  Handles incoming C-FIND response. Just counts number of calls and then forwards
+     *  handling to default DcmSCU handler.
+     *  @param  presID Presentation Context ID
+     *  @param  response The C-FIND response received
+     *  @param  waitForNextResponse Will receive information whether it should be waited
+     *          for further C-FIND responses.
+     *  @return EC_Normal if successful, error otherwise
+     */
+    virtual OFCondition
+    handleFINDResponse(const T_ASC_PresentationContextID presID, QRResponse* response, OFBool& waitForNextResponse)
+    {
+        m_session_counter++;
+        OFCondition result = DcmSCU::handleFINDResponse(presID, response, waitForNextResponse);
+        return result;
+    }
+
+    /** Virtual destructor */
+    virtual ~SessionSCU()
+    {
+    }
+
+    /** Counter for number of DIMSE messages handled
+     */
+    size_t m_session_counter;
+};
+
+// -------------- End of class SessionSCP -------------------------
+
+/** Manually configure Verification SOP class on server
+ *  @param cfg The SCP configuration to modify
+ *  @param sop_class SOP class to be supported
+ *  @param roleOfRequestor role to be negotiated
+ */
+void configure_scp_for_sop_class(DcmSCPConfig& cfg,
+                                 const OFString& sop_class,
+                                 T_ASC_SC_ROLE roleOfRequestor = ASC_SC_ROLE_DEFAULT)
+{
+    cfg.setPort(11112);
+    OFList<OFString> xfers;
+    xfers.push_back(UID_LittleEndianImplicitTransferSyntax);
+    OFCHECK(cfg.addPresentationContext(sop_class, xfers, roleOfRequestor).good());
+}
+
+/** Initiate SCU and perform session with SCP using given SOP class.
+ *  @param called_ae_title The Called AE Title to be used
+ *  @param sop_class The SOP class to negotiate
+ */
+void scu_session(const OFString& called_ae_title, const OFString& sop_class)
+{
+    // Make sure server is up
+    force_sleep(1);
+    // Basic configuration
+    SessionSCU scu;
+    scu.setAETitle("TEST_SCU");
+    scu.setPeerAETitle(called_ae_title);
+    scu.setPeerHostName("localhost");
+    scu.setPeerPort(11112);
+    OFList<OFString> xfers;
+    xfers.push_back(UID_LittleEndianImplicitTransferSyntax);
+    OFCondition result = scu.addPresentationContext(sop_class, xfers);
+    OFCHECK(result.good());
+    result = scu.initNetwork();
+    OFCHECK(result.good());
+
+    // Start connection
+    result = scu.negotiateAssociation();
+    OFCHECK(result.good());
+
+    // Build simple query
+    DcmDataset query;
+    query.putAndInsertOFStringArray(DCM_QueryRetrieveLevel, "PATIENT");
+    query.putAndInsertOFStringArray(DCM_PatientID, "0815");
+    // Send FIND, GET (TODO), or MOVE
+    if (sop_class == UID_FINDPatientRootQueryRetrieveInformationModel)
+    {
+        result = scu.sendFINDRequest(1, &query, NULL);
+    }
+    else if (sop_class == UID_MOVEPatientRootQueryRetrieveInformationModel)
+    {
+        result = scu.sendMOVERequest(3, "TEST_SCU", &query, NULL);
+    }
+    // Check whether session worked by comparing response count
+    OFCHECK(scu.m_session_counter == NUM_DIMSE_REQUESTS);
+    OFCHECK(result.good());
+    // Release association
+    result = scu.releaseAssociation();
+    OFCHECK(result.good());
+    return;
+}
+
+// Test case to check SCU session handling for C-FIND, C-MOVE and C-GET
+OFTEST_FLAGS(dcmnet_scu_session_handler, EF_Slow)
+{
+    // Configure SCP and start it.
+    SessionSCP scp;
+    DcmSCPConfig& config = scp.getConfig();
+    configure_scp_for_sop_class(config, UID_FINDPatientRootQueryRetrieveInformationModel);
+    configure_scp_for_sop_class(config, UID_GETPatientRootQueryRetrieveInformationModel);
+    configure_scp_for_sop_class(config, UID_MOVEPatientRootQueryRetrieveInformationModel);
+    config.setConnectionBlockingMode(DUL_BLOCK);
+    scp.start();
+
+    // Send FIND, and wait to be sure SCP has time to exit
+    scu_session("FIND_SESSION", UID_FINDPatientRootQueryRetrieveInformationModel);
+    force_sleep(1);
+    scp.join();
+
+    // Send MOVE, and wait to be sure SCP has time to exit
+    scp.start();
+    scu_session("MOVE_SESSION", UID_MOVEPatientRootQueryRetrieveInformationModel);
+    force_sleep(1);
+    scp.join();
+
+    // TODO: Test C-GET
+}
+
+#endif // WITH_THREADS
index 728f39fe059f56a642cc961b01e3ce553b407a27..725e5b6ea3cc8769597d360128621e41cbd396b5 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2018, Open Connections GmbH
+ *  Copyright (C) 2018-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -64,7 +64,7 @@ public:
 
     private:
 
-      // Make sure the Parametric Map object (and no one else) can use the constructor below.
+      /// Make sure the Parametric Map object (and no one else) can use the constructor below.
       friend class DPMParametricMapIOD;
 
       /** Create Frames object in DPMParametricMapIOD (see friend declaration above)
index e945cfc196f2e7f712d67eefbfa1c25c9bb9f6f8..42bdd71d1e6e56cc51ef9868bed38562ba53571d 100644 (file)
@@ -50,7 +50,8 @@ dpmmodparametricmapimage.o: dpmmodparametricmapimage.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
@@ -58,17 +59,15 @@ dpmmodparametricmapimage.o: dpmmodparametricmapimage.cc \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../include/dcmtk/dcmpmap/dpmmodparametricmapimage.h \
  ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
  ../include/dcmtk/dcmpmap/dpmdef.h
@@ -124,7 +123,8 @@ dpmmodparametricmapseries.o: dpmmodparametricmapseries.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
@@ -132,17 +132,15 @@ dpmmodparametricmapseries.o: dpmmodparametricmapseries.cc \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../include/dcmtk/dcmpmap/dpmmodparametricmapseries.h \
  ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
  ../include/dcmtk/dcmpmap/dpmdef.h \
@@ -200,7 +198,9 @@ dpmmodparametricmapseries.o: dpmmodparametricmapseries.cc \
 dpmparametricmapbase.o: dpmparametricmapbase.cc \
  ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
@@ -208,14 +208,13 @@ dpmparametricmapbase.o: dpmparametricmapbase.cc \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -241,29 +240,27 @@ dpmparametricmapbase.o: dpmparametricmapbase.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../include/dcmtk/dcmpmap/dpmtypes.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
@@ -324,10 +321,10 @@ dpmparametricmapbase.o: dpmparametricmapbase.cc \
  ../include/dcmtk/dcmpmap/dpmdef.h \
  ../include/dcmtk/dcmpmap/dpmparametricmapbase.h \
  ../../dcmfg/include/dcmtk/dcmfg/fginterface.h \
- ../../dcmfg/include/dcmtk/dcmfg/fgtypes.h \
- ../../dcmfg/include/dcmtk/dcmfg/fgdefine.h \
  ../../dcmfg/include/dcmtk/dcmfg/fg.h \
  ../../dcmfg/include/dcmtk/dcmfg/fgbase.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgdefine.h \
  ../../dcmfg/include/dcmtk/dcmfg/fgderimg.h \
  ../../dcmfg/include/dcmtk/dcmfg/fgfracon.h \
  ../../dcmfg/include/dcmtk/dcmfg/fgframeanatomy.h \
@@ -340,29 +337,29 @@ dpmparametricmapbase.o: dpmparametricmapbase.cc \
  ../../dcmfg/include/dcmtk/dcmfg/fgrealworldvaluemapping.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodcontentitemmacro.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodimage.h \
- ../../ofstd/include/dcmtk/ofstd/ofvriant.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/variant.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/helpers.h \
- ../../ofstd/include/dcmtk/ofstd/ofalign.h \
- ../../ofstd/include/dcmtk/ofstd/ofdiag.h \
- ../../ofstd/include/dcmtk/ofstd/diag/push.def \
- ../../ofstd/include/dcmtk/ofstd/diag/cnvrsn.def \
- ../../ofstd/include/dcmtk/ofstd/diag/vsprfw.def \
- ../../ofstd/include/dcmtk/ofstd/diag/pop.def \
  ../../dcmiod/include/dcmtk/dcmiod/iodcommn.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
  ../../dcmiod/include/dcmtk/dcmiod/modpatient.h \
  ../../dcmiod/include/dcmtk/dcmiod/modpatientstudy.h \
  ../../ofstd/include/dcmtk/ofstd/ofoption.h \
- ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
- ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
- ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
- ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
+ ../../ofstd/include/dcmtk/ofstd/ofalign.h \
  ../../dcmiod/include/dcmtk/dcmiod/modsopcommon.h \
- ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h \
  ../../dcmiod/include/dcmtk/dcmiod/modgeneralimage.h \
  ../../dcmiod/include/dcmtk/dcmiod/modimagepixelvariant.h \
  ../../dcmiod/include/dcmtk/dcmiod/modimagepixelbase.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvriant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/variant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/helpers.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdiag.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/push.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/cnvrsn.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/vsprfw.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/pop.def \
  ../../dcmiod/include/dcmtk/dcmiod/modacquisitioncontext.h \
  ../../dcmiod/include/dcmtk/dcmiod/modenhequipment.h \
  ../../dcmiod/include/dcmtk/dcmiod/modmultiframedimension.h \
@@ -376,22 +373,18 @@ dpmparametricmapiod.o: dpmparametricmapiod.cc \
  ../include/dcmtk/dcmpmap/dpmparametricmapiod.h \
  ../../dcmiod/include/dcmtk/dcmiod/modimagepixelbase.h \
  ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
- ../../ofstd/include/dcmtk/ofstd/ofmem.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
@@ -403,10 +396,14 @@ dpmparametricmapiod.o: dpmparametricmapiod.cc \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -431,14 +428,13 @@ dpmparametricmapiod.o: dpmparametricmapiod.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../include/dcmtk/dcmpmap/dpmparametricmapbase.h \
  ../../dcmfg/include/dcmtk/dcmfg/fginterface.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
@@ -495,10 +491,10 @@ dpmparametricmapiod.o: dpmparametricmapiod.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../../dcmfg/include/dcmtk/dcmfg/fgtypes.h \
- ../../dcmfg/include/dcmtk/dcmfg/fgdefine.h \
  ../../dcmfg/include/dcmtk/dcmfg/fg.h \
  ../../dcmfg/include/dcmtk/dcmfg/fgbase.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgdefine.h \
  ../../dcmfg/include/dcmtk/dcmfg/fgderimg.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
  ../../dcmfg/include/dcmtk/dcmfg/fgfracon.h \
@@ -512,28 +508,28 @@ dpmparametricmapiod.o: dpmparametricmapiod.cc \
  ../../dcmfg/include/dcmtk/dcmfg/fgrealworldvaluemapping.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodcontentitemmacro.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodimage.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodcommn.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modpatient.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modpatientstudy.h \
+ ../../ofstd/include/dcmtk/ofstd/ofoption.h \
+ ../../ofstd/include/dcmtk/ofstd/ofalign.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modsopcommon.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralimage.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixelvariant.h \
  ../../ofstd/include/dcmtk/ofstd/ofvriant.h \
  ../../ofstd/include/dcmtk/ofstd/variadic/variant.h \
  ../../ofstd/include/dcmtk/ofstd/variadic/helpers.h \
- ../../ofstd/include/dcmtk/ofstd/ofalign.h \
  ../../ofstd/include/dcmtk/ofstd/ofdiag.h \
  ../../ofstd/include/dcmtk/ofstd/diag/push.def \
  ../../ofstd/include/dcmtk/ofstd/diag/cnvrsn.def \
  ../../ofstd/include/dcmtk/ofstd/diag/vsprfw.def \
  ../../ofstd/include/dcmtk/ofstd/diag/pop.def \
- ../../dcmiod/include/dcmtk/dcmiod/iodcommn.h \
- ../../dcmiod/include/dcmtk/dcmiod/modpatient.h \
- ../../dcmiod/include/dcmtk/dcmiod/modpatientstudy.h \
- ../../ofstd/include/dcmtk/ofstd/ofoption.h \
- ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
- ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
- ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
- ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
- ../../dcmiod/include/dcmtk/dcmiod/modsopcommon.h \
- ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h \
- ../../dcmiod/include/dcmtk/dcmiod/modgeneralimage.h \
- ../../dcmiod/include/dcmtk/dcmiod/modimagepixelvariant.h \
  ../../dcmiod/include/dcmtk/dcmiod/modacquisitioncontext.h \
  ../../dcmiod/include/dcmtk/dcmiod/modenhequipment.h \
  ../../dcmiod/include/dcmtk/dcmiod/modmultiframedimension.h \
@@ -665,6 +661,5 @@ dpmtypes.o: dpmtypes.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
  ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
  ../include/dcmtk/dcmpmap/dpmdef.h
index 18feaf660f35079e60daaefc767fe90a5bb6fd25..1b5e059058135d620fc93aff197c7a21d1fecd35 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016-2018, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -367,34 +367,6 @@ private:
 };
 
 
-template<>
-Uint8* DPMParametricMapIOD::WriteVisitor::DcmElementOf<IODImagePixelModule<Uint8> >::getData(const size_t size)
-{
-  if (m_pElement)
-  if (m_pElement->setVR(EVR_OB).good())
-  {
-    Uint8* result;
-    if (m_pElement->createUint8Array(OFstatic_cast(Uint32, size), result).good())
-      return result;
-  }
-  return OFnullptr;
-}
-
-
-template<>
-Sint8* DPMParametricMapIOD::WriteVisitor::DcmElementOf<IODImagePixelModule<Sint8> >::getData(const size_t size)
-{
-  if (m_pElement)
-  if (m_pElement->setVR(EVR_OB).good())
-  {
-    Uint8* result;
-    if (m_pElement->createUint8Array(OFstatic_cast(Uint32, size), result).good())
-      return OFreinterpret_cast(Sint8*, result);
-  }
-  return OFnullptr;
-}
-
-
 template<>
 Uint16* DPMParametricMapIOD::WriteVisitor::DcmElementOf<IODImagePixelModule<Uint16> >::getData(const size_t size /* num total pixels */)
 {
index 399af7aea38b362c3db6bae14b11ab9c33c94b0b..15644d2573a7c674e836ce1528d52b832e62c1a5 100644 (file)
@@ -1,5 +1,5 @@
 /*
- *  Copyright (C) 1999-2019, OFFIS e.V.
+ *  Copyright (C) 1999-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -543,11 +543,11 @@ static OFCondition updateJobList(
   const char *spoolFolder = dvi.getSpoolFolder();
 
 #ifdef HAVE_WINDOWS_H
-  WIN32_FIND_DATA stWin32FindData;
+  WIN32_FIND_DATAA stWin32FindData;
   OFString currentdir = spoolFolder;
   currentdir += "\\*";
 
-  HANDLE hFile = FindFirstFile(currentdir.c_str(), &stWin32FindData);
+  HANDLE hFile = FindFirstFileA(currentdir.c_str(), &stWin32FindData);
   int ret = (hFile != INVALID_HANDLE_VALUE);
   while (ret)
   {
@@ -595,7 +595,7 @@ static OFCondition updateJobList(
       }
 
 #ifdef HAVE_WINDOWS_H
-      ret = FindNextFile(hFile, &stWin32FindData);
+      ret = FindNextFileA(hFile, &stWin32FindData);
   } /* while */
   if(hFile != INVALID_HANDLE_VALUE)
   {
@@ -1067,7 +1067,7 @@ int main(int argc, char *argv[])
         OFStandard::sleep((unsigned int)opt_sleep);
         if (EC_Normal != updateJobList(jobList, dvi, terminateFlag, jobNamePrefix.c_str()))
         {
-          OFLOG_FATAL(dcmprscuLogger, "spooler: non recoverable error occured, terminating");
+          OFLOG_FATAL(dcmprscuLogger, "spooler: non recoverable error occurred, terminating");
           return 10;
         }
         // static OFCondition updateJobList(jobList, dvi, terminateFlag, jobNamePrefix.c_str());
index c7273f244d37a605f94f3629c5e63f85590e031a..574f7603ad59d8bd93bc8e7b213dd76a743c50a4 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1999-2019, OFFIS e.V.
+ *  Copyright (C) 1999-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -80,9 +80,12 @@ static int addOverlay(const char *filename,
                         for (unsigned long xs = 0; xs < xsize; xs++)
                         {
                             while (input.get(c) && !isdigit(OFstatic_cast(unsigned char, c)));  // skip non-numeric chars
-                            input.putback(c);
-                            input >> value;
-                            if (value)
+                            if (!isdigit(OFstatic_cast(unsigned char, c)))
+                            {
+                              OFLOG_ERROR(dcmpsprtLogger, "syntax error in PBM file '" << filename << "'");
+                              return 0;
+                            }
+                            if (c != '0')
                                 *p = gray;
                             p++;
                         }
@@ -90,7 +93,7 @@ static int addOverlay(const char *filename,
                     }
                     return 1;
                 } else
-                    OFLOG_ERROR(dcmpsprtLogger, "invalid position for overlay PBM file '" << filename);
+                    OFLOG_ERROR(dcmpsprtLogger, "invalid position for overlay PBM file '" << filename << "'");
             } else
                 OFLOG_ERROR(dcmpsprtLogger, "overlay PBM file '" << filename << "' has no magic number P1");
         } else
@@ -445,7 +448,7 @@ int main(int argc, char *argv[])
     /* dump printer characteristics if requested */
     const char *currentPrinter = dvi.getCurrentPrinter();
 
-    if ((opt_img_request_size) && (!dvi.getTargetPrinterSupportsRequestedImageSize(opt_printerID)))
+    if ((opt_img_request_size) && (!dvi.getTargetPrinterSupportsRequestedImageSize(currentPrinter)))
       OFLOG_WARN(dcmpsprtLogger, "printer does not support requested image size");
 
     if (EC_Normal != dvi.getPrintHandler().setImageDisplayFormat(opt_columns, opt_rows))
@@ -645,7 +648,7 @@ int main(int argc, char *argv[])
       {
         // no need to do this manually if we are spooling - spoolPrintJob() will do this anyway.
         OFLOG_WARN(dcmpsprtLogger, "writing DICOM stored print object to database.");
-        if (EC_Normal != dvi.saveStoredPrint(dvi.getTargetPrinterSupportsRequestedImageSize(opt_printerID)))
+        if (EC_Normal != dvi.saveStoredPrint(dvi.getTargetPrinterSupportsRequestedImageSize(currentPrinter)))
         {
           OFLOG_ERROR(dcmpsprtLogger, "error during creation of DICOM stored print object");
         }
index 2d108c88cfd5225aa785afc718a6dda79ca3a675..0a578c5edba8a29336382c5bcba39e6c7ff06f4d 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1999-2019, OFFIS e.V.
+ *  Copyright (C) 1999-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -547,7 +547,7 @@ static OFCondition storeSCP(
     dcmtk_flock(lockfd, LOCK_EX);
 #endif
 
-    /* we must still retrieve the data set even if some error has occured */
+    /* we must still retrieve the data set even if some error has occurred */
     StoreContext context(dbhandle, status, imageFileName, &dcmff, opt_correctUIDPadding);
 
     if (opt_bitpreserving)
@@ -1315,8 +1315,8 @@ int main(int argc, char *argv[])
               dropAssociation(&assoc);
             } else if (pid > 0)
             {
-              /* parent process */
-              assoc = NULL;
+              /* we're the parent process, close accepted socket and continue */
+              dropAssociation(&assoc);
             } else {
               /* child process */
 
@@ -1349,15 +1349,15 @@ int main(int argc, char *argv[])
             // initialize startup info
             const char *receiver_application = dvi.getReceiverName();
             PROCESS_INFORMATION procinfo;
-            STARTUPINFO sinfo;
+            STARTUPINFOA sinfo;
             OFBitmanipTemplate<char>::zeroMem((char *)&sinfo, sizeof(sinfo));
             sinfo.cb = sizeof(sinfo);
             char commandline[4096];
             sprintf(commandline, "%s %s %s", receiver_application, opt_cfgName, opt_cfgID);
 #ifdef DEBUG
-            if (CreateProcess(NULL, commandline, NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo))
+            if (CreateProcessA(NULL, commandline, NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo))
 #else
-            if (CreateProcess(NULL, commandline, NULL, NULL, 0, DETACHED_PROCESS, NULL, NULL, &sinfo, &procinfo))
+            if (CreateProcessA(NULL, commandline, NULL, NULL, 0, DETACHED_PROCESS, NULL, NULL, &sinfo, &procinfo))
 #endif
             {
 #ifdef WITH_OPENSSL
index b3e3a0c2a2e9155e7efcfb2f87eb598239f3bd0c..bdf223c7bb34a205e8413e2bc99d15873946b006 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2012, OFFIS e.V.
+ *  Copyright (C) 1998-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -92,9 +92,9 @@ public:
 
    /** sets bounding box for this text object.
     *  @param TLHC_x bounding box top-lefthand corner X value
-    *  @param TLHC_x bounding box top-lefthand corner Y value
+    *  @param TLHC_y bounding box top-lefthand corner Y value
     *  @param BRHC_x bounding box bottom-righthand corner X value
-    *  @param BRHC_x bounding box bottom-righthand corner Y value
+    *  @param BRHC_y bounding box bottom-righthand corner Y value
     *  @param unit bounding box annotation units (pixel/display)
     *  @param justification bounding box horizontal justification (left/right/center)
     *  @return EC_Normal if successful, an error code otherwise.
index 8fed5dd9aeb50892fbd5c4bf3c79e331041e9784..ef66ce2feb8f274e14e7a4767e0b351b53525c5c 100644 (file)
@@ -306,6 +306,7 @@ dviface.o: dviface.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmsign/include/dcmtk/dcmsign/sitypes.h \
  ../../dcmsign/include/dcmtk/dcmsign/sidefine.h \
  ../../dcmsign/include/dcmtk/dcmsign/dcsignat.h \
+ ../../dcmsign/include/dcmtk/dcmsign/sipurpos.h \
  ../../dcmsr/include/dcmtk/dcmsr/dsrdoc.h \
  ../../dcmsr/include/dcmtk/dcmsr/dsrdoctr.h \
  ../../dcmsr/include/dcmtk/dcmsr/dsrdocst.h \
@@ -4781,6 +4782,7 @@ dvsighdl.o: dvsighdl.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmsign/include/dcmtk/dcmsign/sipurpos.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
index 43c1bf5d48de8b24bd1badc33765e70c9f255249..d5f452267bcad4d40de061d2a5eeb2c1c81a99c9 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2019, OFFIS e.V.
+ *  Copyright (C) 1998-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -2236,7 +2236,7 @@ OFCondition DVInterface::sendIOD(const char * targetID,
 
   // initialize startup info
   PROCESS_INFORMATION procinfo;
-  STARTUPINFO sinfo;
+  STARTUPINFOA sinfo;
   OFBitmanipTemplate<char>::zeroMem((char *)&sinfo, sizeof(sinfo));
   sinfo.cb = sizeof(sinfo);
   char commandline[4096];
@@ -2246,9 +2246,9 @@ OFCondition DVInterface::sendIOD(const char * targetID,
       studyUID, seriesUID);
   else sprintf(commandline, "%s %s %s %s", sender_application, configPath.c_str(), targetID, studyUID);
 #ifdef DEBUG
-  if (CreateProcess(NULL, commandline, NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo))
+  if (CreateProcessA(NULL, commandline, NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo))
 #else
-  if (CreateProcess(NULL, commandline, NULL, NULL, 0, DETACHED_PROCESS, NULL, NULL, &sinfo, &procinfo))
+  if (CreateProcessA(NULL, commandline, NULL, NULL, 0, DETACHED_PROCESS, NULL, NULL, &sinfo, &procinfo))
 #endif
   {
     return EC_Normal;
@@ -2298,15 +2298,15 @@ OFCondition DVInterface::startReceiver()
     // Windows version - call CreateProcess()
     // initialize startup info
     PROCESS_INFORMATION procinfo;
-    STARTUPINFO sinfo;
+    STARTUPINFOA sinfo;
     OFBitmanipTemplate<char>::zeroMem((char *)&sinfo, sizeof(sinfo));
     sinfo.cb = sizeof(sinfo);
     char commandline[4096];
     sprintf(commandline, "%s %s %s", receiver_application, configPath.c_str(), getTargetID(i, DVPSE_receiver));
 #ifdef DEBUG
-    if (CreateProcess(NULL, commandline, NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo))
+    if (CreateProcessA(NULL, commandline, NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo))
 #else
-    if (CreateProcess(NULL, commandline, NULL, NULL, 0, DETACHED_PROCESS, NULL, NULL, &sinfo, &procinfo))
+    if (CreateProcessA(NULL, commandline, NULL, NULL, 0, DETACHED_PROCESS, NULL, NULL, &sinfo, &procinfo))
 #endif
     {
       // continue loop
@@ -2353,15 +2353,15 @@ OFCondition DVInterface::terminateReceiver()
   // Windows version - call CreateProcess()
   // initialize startup info
   PROCESS_INFORMATION procinfo;
-  STARTUPINFO sinfo;
+  STARTUPINFOA sinfo;
   OFBitmanipTemplate<char>::zeroMem((char *)&sinfo, sizeof(sinfo));
   sinfo.cb = sizeof(sinfo);
   char commandline[4096];
   sprintf(commandline, "%s %s %s", receiver_application, configPath.c_str(), "--terminate");
 #ifdef DEBUG
-  if (CreateProcess(NULL, commandline, NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo))
+  if (CreateProcessA(NULL, commandline, NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo))
 #else
-  if (CreateProcess(NULL, commandline, NULL, NULL, 0, DETACHED_PROCESS, NULL, NULL, &sinfo, &procinfo))
+  if (CreateProcessA(NULL, commandline, NULL, NULL, 0, DETACHED_PROCESS, NULL, NULL, &sinfo, &procinfo))
 #endif
   {
     // continue loop
@@ -2426,7 +2426,7 @@ OFCondition DVInterface::startQueryRetrieveServer()
   // Windows version - call CreateProcess()
   // initialize startup info
   PROCESS_INFORMATION procinfo;
-  STARTUPINFO sinfo;
+  STARTUPINFOA sinfo;
   OFBitmanipTemplate<char>::zeroMem((char *)&sinfo, sizeof(sinfo));
   sinfo.cb = sizeof(sinfo);
   char commandline[4096];
@@ -2442,9 +2442,9 @@ OFCondition DVInterface::startQueryRetrieveServer()
   }
 
 #ifdef DEBUG
-  if (CreateProcess(NULL, commandline, NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo))
+  if (CreateProcessA(NULL, commandline, NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo))
 #else
-  if (CreateProcess(NULL, commandline, NULL, NULL, 0, DETACHED_PROCESS, NULL, NULL, &sinfo, &procinfo))
+  if (CreateProcessA(NULL, commandline, NULL, NULL, 0, DETACHED_PROCESS, NULL, NULL, &sinfo, &procinfo))
 #endif
   {
     return EC_Normal;
@@ -2972,6 +2972,7 @@ OFCondition DVInterface::saveStoredPrint(
       if (prependDateTime)
       {
         OFDateTime::getCurrentDateTime().getISOFormattedDateTime(text, OFFalse /*showSeconds*/);
+        text += " ";
       }
       if (prependPrinterName)
       {
@@ -3387,7 +3388,7 @@ OFCondition DVInterface::startPrintSpooler()
   const char *printer = NULL;
   unsigned long sleepingTime = getSpoolerSleep();
   if (sleepingTime==0) sleepingTime=1; // default
-  char sleepStr[20];
+  char sleepStr[30];
   sprintf(sleepStr, "%lu", sleepingTime);
   OFBool detailedLog = getDetailedLog();
 
@@ -3432,7 +3433,7 @@ OFCondition DVInterface::startPrintSpooler()
     // Windows version - call CreateProcess()
     // initialize startup info
     PROCESS_INFORMATION procinfo;
-    STARTUPINFO sinfo;
+    STARTUPINFOA sinfo;
     OFBitmanipTemplate<char>::zeroMem((char *)&sinfo, sizeof(sinfo));
     sinfo.cb = sizeof(sinfo);
     char commandline[4096];
@@ -3445,9 +3446,9 @@ OFCondition DVInterface::startPrintSpooler()
         printJobIdentifier.c_str(), printer, configPath.c_str(), sleepStr);
     }
 #ifdef DEBUG
-    if (0 == CreateProcess(NULL, commandline, NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo))
+    if (0 == CreateProcessA(NULL, commandline, NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo))
 #else
-    if (0 == CreateProcess(NULL, commandline, NULL, NULL, 0, DETACHED_PROCESS, NULL, NULL, &sinfo, &procinfo))
+    if (0 == CreateProcessA(NULL, commandline, NULL, NULL, 0, DETACHED_PROCESS, NULL, NULL, &sinfo, &procinfo))
 #endif
     {
       DCMPSTAT_ERROR("Unable to execute '" << spooler_application << "'");
@@ -3567,7 +3568,7 @@ OFCondition DVInterface::startPrintServer()
     // Windows version - call CreateProcess()
     // initialize startup info
     PROCESS_INFORMATION procinfo;
-    STARTUPINFO sinfo;
+    STARTUPINFOA sinfo;
     OFBitmanipTemplate<char>::zeroMem((char *)&sinfo, sizeof(sinfo));
     sinfo.cb = sizeof(sinfo);
     char commandline[4096];
@@ -3578,9 +3579,9 @@ OFCondition DVInterface::startPrintServer()
       sprintf(commandline, "%s --logfile --printer %s --config %s", application, printer, configPath.c_str());
     }
 #ifdef DEBUG
-    if (0 == CreateProcess(NULL, commandline, NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo))
+    if (0 == CreateProcessA(NULL, commandline, NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo))
 #else
-    if (0 == CreateProcess(NULL, commandline, NULL, NULL, 0, DETACHED_PROCESS, NULL, NULL, &sinfo, &procinfo))
+    if (0 == CreateProcessA(NULL, commandline, NULL, NULL, 0, DETACHED_PROCESS, NULL, NULL, &sinfo, &procinfo))
 #endif
     {
       DCMPSTAT_ERROR("Unable to execute '" << application << "'");
@@ -3830,7 +3831,7 @@ OFCondition DVInterface::printSCUcreateBasicFilmSession(DVPSPrintMessageHandler&
   OFCondition result = EC_Normal;
   DcmDataset dset;
   DcmElement *delem = NULL;
-  char buf[20];
+  char buf[30];
 
   if ((EC_Normal==result)&&(printerMediumType.size() > 0))
   {
@@ -3922,15 +3923,15 @@ OFCondition DVInterface::startExternalApplication(const char *application, const
 
   // initialize startup info
   PROCESS_INFORMATION procinfo;
-  STARTUPINFO sinfo;
+  STARTUPINFOA sinfo;
   OFBitmanipTemplate<char>::zeroMem((char *)&sinfo, sizeof(sinfo));
   sinfo.cb = sizeof(sinfo);
   char commandline[4096];
   sprintf(commandline, "%s %s", application, filename);
 #ifdef DEBUG
-  if (CreateProcess(NULL, commandline, NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo))
+  if (CreateProcessA(NULL, commandline, NULL, NULL, 0, 0, NULL, NULL, &sinfo, &procinfo))
 #else
-  if (CreateProcess(NULL, commandline, NULL, NULL, 0, DETACHED_PROCESS, NULL, NULL, &sinfo, &procinfo))
+  if (CreateProcessA(NULL, commandline, NULL, NULL, 0, DETACHED_PROCESS, NULL, NULL, &sinfo, &procinfo))
 #endif
   {
     return EC_Normal;
index f5efccf64b949650bc55ff99e1169132e2fafb50..be3c81fe0465e0fe9ef0d41ee0f3d4ec8a52cc44 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2017, OFFIS e.V.
+ *  Copyright (C) 1998-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -209,6 +209,7 @@ OFCondition DVPSCurve::read(DcmItem &dset, Uint8 group)
     case EVR_OB:
     case EVR_OW:
     case EVR_ox:
+    case EVR_px:
     case EVR_US:
 
       if (EC_Normal == d_curveData->getUint8Array(pui8))
index a64b81875197f85787413c946c7d65fe16ad2d42..99918e7734577807b803414a6744ae83f3413bf4 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2001-2010, OFFIS e.V.
+ *  Copyright (C) 2001-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -151,7 +151,7 @@ void DVSignatureHandler::printSignatureItemPosition(DcmStack& stack, STD_NAMESPA
   unsigned long sqCard=0;
   const char *tagname = NULL;
   unsigned long m=0;
-  char buf[20];
+  char buf[30];
   OFBool printed = OFFalse;
   
   if (stack.card() > 2)
@@ -333,6 +333,7 @@ void DVSignatureHandler::updateDigitalSignatureInformation(DcmItem& /*dataset*/,
           cert->getCertValidityNotAfter(aString);
           os << aString.c_str() << htmlEndl
              << htmlLine4 << "Public key" << htmlNext;
+          const char *ecname = NULL;
           switch (cert->getKeyType())
           {
             case EKT_RSA:
@@ -341,6 +342,17 @@ void DVSignatureHandler::updateDigitalSignatureInformation(DcmItem& /*dataset*/,
             case EKT_DSA:
               os << "DSA, " << cert->getCertKeyBits() << " bits" << htmlEndl;
               break;
+            case EKT_EC:
+              ecname = cert->getCertCurveName();
+              if (ecname)
+              {
+                os << "EC, curve " << ecname << ", " << cert->getCertKeyBits() << " bits";
+              }
+              else
+              {
+                os << "EC, " << cert->getCertKeyBits() << " bits";
+              }
+              break;
             case EKT_DH:
               os << "DH, " << cert->getCertKeyBits() << " bits" << htmlEndl;
               break;
index b932a2351c8894ec0b112738e52764d5a4176caa..620793daed221c9943b2f473909d71649ad2479e 100644 (file)
@@ -761,6 +761,12 @@ BasicVoiceAudioWaveformStorage                       1.2.840.10008.5.1.4.1.1.9.4
 GeneralAudioWaveformStorage                          1.2.840.10008.5.1.4.1.1.9.4.2
 ArterialPulseWaveformStorage                         1.2.840.10008.5.1.4.1.1.9.5.1
 RespiratoryWaveformStorage                           1.2.840.10008.5.1.4.1.1.9.6.1
+MultichannelRespiratoryWaveformStorage               1.2.840.10008.5.1.4.1.1.9.6.2
+RoutineScalpElectroencephalogramWaveformStorage      1.2.840.10008.5.1.4.1.1.9.7.1
+ElectromyogramWaveformStorage                        1.2.840.10008.5.1.4.1.1.9.7.2
+ElectrooculogramWaveformStorage                      1.2.840.10008.5.1.4.1.1.9.7.3
+SleepElectroencephalogramWaveformStorage             1.2.840.10008.5.1.4.1.1.9.7.4
+BodyPositionWaveformStorage                          1.2.840.10008.5.1.4.1.1.9.8.1
 RETIRED_StandaloneModalityLUTStorage                 1.2.840.10008.5.1.4.1.1.10
 RETIRED_StandaloneVOILUTStorage                      1.2.840.10008.5.1.4.1.1.11
 GrayscaleSoftcopyPresentationStateStorage            1.2.840.10008.5.1.4.1.1.11.1
@@ -815,6 +821,7 @@ WideFieldOphthalmicPhotogr.3DCoordinatesImageStorage 1.2.840.10008.5.1.4.1.1.77.
 OphthalmicOpticalCoherenceTomogr.EnFaceImageStorage  1.2.840.10008.5.1.4.1.1.77.1.5.7
 OphthalmicOpticalCoh.Tomogr.BscanVolumeAnalysisStor. 1.2.840.10008.5.1.4.1.1.77.1.5.8
 VLWholeSlideMicroscopyImageStorage                   1.2.840.10008.5.1.4.1.1.77.1.6
+DermoscopicPhotographyImageStorage                   1.2.840.10008.5.1.4.1.1.77.1.7
 RETIRED_VLMultiframeImageStorage                     1.2.840.10008.5.1.4.1.1.77.2
 LensometryMeasurementsStorage                        1.2.840.10008.5.1.4.1.1.78.1
 AutorefractionMeasurementsStorage                    1.2.840.10008.5.1.4.1.1.78.2
@@ -854,6 +861,8 @@ ContentAssessmentResultsStorage                      1.2.840.10008.5.1.4.1.1.90.
 EncapsulatedPDFStorage                               1.2.840.10008.5.1.4.1.1.104.1
 EncapsulatedCDAStorage                               1.2.840.10008.5.1.4.1.1.104.2
 EncapsulatedSTLStorage                               1.2.840.10008.5.1.4.1.1.104.3
+EncapsulatedOBJStorage                               1.2.840.10008.5.1.4.1.1.104.4
+EncapsulatedMTLStorage                               1.2.840.10008.5.1.4.1.1.104.5
 PositronEmissionTomographyImageStorage               1.2.840.10008.5.1.4.1.1.128
 LegacyConvertedEnhancedPETImageStorage               1.2.840.10008.5.1.4.1.1.128.1
 RETIRED_StandalonePETCurveStorage                    1.2.840.10008.5.1.4.1.1.129
@@ -873,6 +882,13 @@ RTPhysicianIntentStorage                             1.2.840.10008.5.1.4.1.1.481
 RTSegmentAnnotationStorage                           1.2.840.10008.5.1.4.1.1.481.11
 RTRadiationSetStorage                                1.2.840.10008.5.1.4.1.1.481.12
 CArmPhotonElectronRadiationStorage                   1.2.840.10008.5.1.4.1.1.481.13
+TomotherapeuticRadiationStorage                      1.2.840.10008.5.1.4.1.1.481.14
+RoboticArmRadiationStorage                           1.2.840.10008.5.1.4.1.1.481.15
+RTRadiationRecordSetStorage                          1.2.840.10008.5.1.4.1.1.481.16
+RTRadiationSalvageRecordStorage                      1.2.840.10008.5.1.4.1.1.481.17
+TomotherapeuticRadiationRecordStorage                1.2.840.10008.5.1.4.1.1.481.18
+CArmPhotonElectronRadiationRecordStorage             1.2.840.10008.5.1.4.1.1.481.19
+RoboticRadiationRecordStorage                        1.2.840.10008.5.1.4.1.1.481.20
 DICOS_CTImageStorage                                 1.2.840.10008.5.1.4.1.1.501.1
 DICOS_DigitalXRayImageStorageForPresentation         1.2.840.10008.5.1.4.1.1.501.2.1
 DICOS_DigitalXRayImageStorageForProcessing           1.2.840.10008.5.1.4.1.1.501.2.2
@@ -1077,6 +1093,6 @@ It is an error if no data dictionary can be loaded.
 
 \section dcmqrscp_copyright COPYRIGHT
 
-Copyright (C) 1993-2019 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 1993-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index 881db973ee5c2663b264fb3ed7a9030c9ce9aecc..dcafed600ae6b038e2132747c3a5e3e7aa6f8f9e 100644 (file)
@@ -1,5 +1,5 @@
 #
-#  Copyright (C) 2017-2019, OFFIS e.V.
+#  Copyright (C) 2017-2020, OFFIS e.V.
 #  All rights reserved.  See COPYRIGHT file for details.
 #
 #  This software and supporting documentation were developed by
@@ -231,14 +231,21 @@ PresentationContext128 = DRAFT_WaveformStorage\UncompressedOrZlib
 #
 # - AcquisitionContextSRStorage
 # - AdvancedBlendingPresentationStateStorage
+# - BodyPositionWaveformStorage
 # - BreastProjectionXRayImageStorageForPresentation
 # - BreastProjectionXRayImageStorageForProcessing
+# - CArmPhotonElectronRadiationRecordStorage
 # - CArmPhotonElectronRadiationStorage
 # - ColorPaletteStorage
 # - CompositingPlanarMPRVolumetricPresentationStateStorage
 # - ContentAssessmentResultsStorage
 # - CTDefinedProcedureProtocolStorage
 # - CTPerformedProcedureProtocolStorage
+# - DermoscopicPhotographyImageStorage
+# - ElectromyogramWaveformStorage
+# - ElectrooculogramWaveformStorage
+# - EncapsulatedMTLStorage
+# - EncapsulatedOBJStorage
 # - EncapsulatedSTLStorage
 # - ExtensibleSRStorage
 # - GrayscalePlanarMPRVolumetricPresentationStateStorage
@@ -246,6 +253,7 @@ PresentationContext128 = DRAFT_WaveformStorage\UncompressedOrZlib
 # - LegacyConvertedEnhancedCTImageStorage
 # - LegacyConvertedEnhancedMRImageStorage
 # - LegacyConvertedEnhancedPETImageStorage
+# - MultichannelRespiratoryWaveformStorage
 # - MultipleVolumeRenderingVolumetricPresentationStateStorage
 # - OphthalmicOpticalCoherenceTomographyBscanVolumeAnalysisStorage
 # - OphthalmicOpticalCoherenceTomographyEnFaceImageStorage
@@ -254,12 +262,20 @@ PresentationContext128 = DRAFT_WaveformStorage\UncompressedOrZlib
 # - PerformedImagingAgentAdministrationSRStorage
 # - PlannedImagingAgentAdministrationSRStorage
 # - RadiopharmaceuticalRadiationDoseSRStorage
+# - RoboticArmRadiationStorage
+# - RoboticRadiationRecordStorage
+# - RoutineScalpElectroencephalogramWaveformStorage
 # - RTBrachyApplicationSetupDeliveryInstructionStorage
 # - RTPhysicianIntentStorage
+# - RTRadiationRecordSetStorage
+# - RTRadiationSalvageRecordStorage
 # - RTRadiationSetStorage
 # - RTSegmentAnnotationStorage
 # - SegmentedVolumeRenderingVolumetricPresentationStateStorage
 # - SimplifiedAdultEchoSRStorage
+# - SleepElectroencephalogramWaveformStorage
+# - TomotherapeuticRadiationRecordStorage
+# - TomotherapeuticRadiationStorage
 # - TractographyResultsStorage
 # - VolumeRenderingVolumetricPresentationStateStorage
 # - WideFieldOphthalmicPhotographyStereographicProjectionImageStorage
@@ -423,9 +439,17 @@ PresentationContext128 = XRayRadiationDoseSRStorage\UncompressedOrZlib
 # the following SOP classes are missing in the above list:
 #
 # - AdvancedBlendingPresentationStateStorage
+# - BodyPositionWaveformStorage
+# - CArmPhotonElectronRadiationRecordStorage
 # - CArmPhotonElectronRadiationStorage
 # - ColorPaletteStorage
+# - DermoscopicPhotographyImageStorage
+# - ElectromyogramWaveformStorage
+# - ElectrooculogramWaveformStorage
+# - EncapsulatedMTLStorage
+# - EncapsulatedOBJStorage
 # - EncapsulatedSTLStorage
+# - MultichannelRespiratoryWaveformStorage
 # - MultipleVolumeRenderingVolumetricPresentationStateStorage
 # - OphthalmicOpticalCoherenceTomographyBscanVolumeAnalysisStorage
 # - OphthalmicOpticalCoherenceTomographyEnFaceImageStorage
@@ -433,10 +457,18 @@ PresentationContext128 = XRayRadiationDoseSRStorage\UncompressedOrZlib
 # - PerformedImagingAgentAdministrationSRStorage
 # - PlannedImagingAgentAdministrationSRStorage
 # - ProtocolApprovalStorage
+# - RoboticArmRadiationStorage
+# - RoboticRadiationRecordStorage
+# - RoutineScalpElectroencephalogramWaveformStorage
 # - RTPhysicianIntentStorage
+# - RTRadiationRecordSetStorage
+# - RTRadiationSalvageRecordStorage
 # - RTRadiationSetStorage
 # - RTSegmentAnnotationStorage
 # - SegmentedVolumeRenderingVolumetricPresentationStateStorage
+# - SleepElectroencephalogramWaveformStorage
+# - TomotherapeuticRadiationRecordStorage
+# - TomotherapeuticRadiationStorage
 # - VolumeRenderingVolumetricPresentationStateStorage
 #
 # - RETIRED_HardcopyColorImageStorage
@@ -623,9 +655,11 @@ PresentationContext128 = VideoPhotographicImageStorage\MPEG2
 # - AutorefractionMeasurementsStorage
 # - BasicStructuredDisplayStorage
 # - BlendingSoftcopyPresentationStateStorage
+# - BodyPositionWaveformStorage
 # - BreastProjectionXRayImageStorageForPresentation
 # - BreastProjectionXRayImageStorageForProcessing
 # - BreastTomosynthesisImageStorage
+# - CArmPhotonElectronRadiationRecordStorage
 # - CArmPhotonElectronRadiationStorage
 # - CompositingPlanarMPRVolumetricPresentationStateStorage
 # - Comprehensive3DSRStorage
@@ -634,7 +668,12 @@ PresentationContext128 = VideoPhotographicImageStorage\MPEG2
 # - CTDefinedProcedureProtocolStorage
 # - CTPerformedProcedureProtocolStorage
 # - DeformableSpatialRegistrationStorage
+# - DermoscopicPhotographyImageStorage
+# - ElectromyogramWaveformStorage
+# - ElectrooculogramWaveformStorage
 # - EncapsulatedCDAStorage
+# - EncapsulatedMTLStorage
+# - EncapsulatedOBJStorage
 # - EncapsulatedSTLStorage
 # - EnhancedMRColorImageStorage
 # - EnhancedPETImageStorage
@@ -655,6 +694,7 @@ PresentationContext128 = VideoPhotographicImageStorage\MPEG2
 # - LegacyConvertedEnhancedPETImageStorage
 # - LensometryMeasurementsStorage
 # - MacularGridThicknessAndVolumeReportStorage
+# - MultichannelRespiratoryWaveformStorage
 # - MultipleVolumeRenderingVolumetricPresentationStateStorage
 # - OphthalmicAxialMeasurementsStorage
 # - OphthalmicOpticalCoherenceTomographyBscanVolumeAnalysisStorage
@@ -670,21 +710,29 @@ PresentationContext128 = VideoPhotographicImageStorage\MPEG2
 # - RadiopharmaceuticalRadiationDoseSRStorage
 # - RealWorldValueMappingStorage
 # - RespiratoryWaveformStorage
+# - RoboticArmRadiationStorage
+# - RoboticRadiationRecordStorage
+# - RoutineScalpElectroencephalogramWaveformStorage
 # - RTBeamsDeliveryInstructionStorage
 # - RTBrachyApplicationSetupDeliveryInstructionStorage
 # - RTIonBeamsTreatmentRecordStorage
 # - RTIonPlanStorage
 # - RTPhysicianIntentStorage
+# - RTRadiationRecordSetStorage
+# - RTRadiationSalvageRecordStorage
 # - RTRadiationSetStorage
 # - RTSegmentAnnotationStorage
 # - SegmentationStorage
 # - SegmentedVolumeRenderingVolumetricPresentationStateStorage
 # - SimplifiedAdultEchoSRStorage
+# - SleepElectroencephalogramWaveformStorage
 # - SpectaclePrescriptionReportStorage
 # - SubjectiveRefractionMeasurementsStorage
 # - SurfaceScanMeshStorage
 # - SurfaceScanPointCloudStorage
 # - SurfaceSegmentationStorage
+# - TomotherapeuticRadiationRecordStorage
+# - TomotherapeuticRadiationStorage
 # - TractographyResultsStorage
 # - VisualAcuityMeasurementsStorage
 # - VLWholeSlideMicroscopyImageStorage
@@ -863,14 +911,21 @@ Role127 = DRAFT_WaveformStorage\BOTH
 #
 # - AcquisitionContextSRStorage
 # - AdvancedBlendingPresentationStateStorage
+# - BodyPositionWaveformStorage
 # - BreastProjectionXRayImageStorageForPresentation
 # - BreastProjectionXRayImageStorageForProcessing
+# - CArmPhotonElectronRadiationRecordStorage
 # - CArmPhotonElectronRadiationStorage
 # - ColorPaletteStorage
 # - CompositingPlanarMPRVolumetricPresentationStateStorage
 # - ContentAssessmentResultsStorage
 # - CTDefinedProcedureProtocolStorage
 # - CTPerformedProcedureProtocolStorage
+# - DermoscopicPhotographyImageStorage
+# - ElectromyogramWaveformStorage
+# - ElectrooculogramWaveformStorage
+# - EncapsulatedMTLStorage
+# - EncapsulatedOBJStorage
 # - EncapsulatedSTLStorage
 # - ExtensibleSRStorage
 # - GrayscalePlanarMPRVolumetricPresentationStateStorage
@@ -878,6 +933,7 @@ Role127 = DRAFT_WaveformStorage\BOTH
 # - LegacyConvertedEnhancedCTImageStorage
 # - LegacyConvertedEnhancedMRImageStorage
 # - LegacyConvertedEnhancedPETImageStorage
+# - MultichannelRespiratoryWaveformStorage
 # - MultipleVolumeRenderingVolumetricPresentationStateStorage
 # - OphthalmicOpticalCoherenceTomographyBscanVolumeAnalysisStorage
 # - OphthalmicOpticalCoherenceTomographyEnFaceImageStorage
@@ -887,12 +943,20 @@ Role127 = DRAFT_WaveformStorage\BOTH
 # - PlannedImagingAgentAdministrationSRStorage
 # - ProtocolApprovalStorage
 # - RadiopharmaceuticalRadiationDoseSRStorage
+# - RoboticArmRadiationStorage
+# - RoboticRadiationRecordStorage
+# - RoutineScalpElectroencephalogramWaveformStorage
 # - RTBrachyApplicationSetupDeliveryInstructionStorage
 # - RTPhysicianIntentStorage
+# - RTRadiationRecordSetStorage
+# - RTRadiationSalvageRecordStorage
 # - RTRadiationSetStorage
 # - RTSegmentAnnotationStorage
 # - SegmentedVolumeRenderingVolumetricPresentationStateStorage
 # - SimplifiedAdultEchoSRStorage
+# - SleepElectroencephalogramWaveformStorage
+# - TomotherapeuticRadiationRecordStorage
+# - TomotherapeuticRadiationStorage
 # - TractographyResultsStorage
 # - VolumeRenderingVolumetricPresentationStateStorage
 # - WideFieldOphthalmicPhotographyStereographicProjectionImageStorage
@@ -1044,9 +1108,17 @@ Role127 = XRayRadiationDoseSRStorage\BOTH
 # the following SOP classes are missing in the above list:
 #
 # - AdvancedBlendingPresentationStateStorage
+# - BodyPositionWaveformStorage
+# - CArmPhotonElectronRadiationRecordStorage
 # - CArmPhotonElectronRadiationStorage
 # - ColorPaletteStorage
+# - DermoscopicPhotographyImageStorage
+# - ElectromyogramWaveformStorage
+# - ElectrooculogramWaveformStorage
+# - EncapsulatedMTLStorage
+# - EncapsulatedOBJStorage
 # - EncapsulatedSTLStorage
+# - MultichannelRespiratoryWaveformStorage
 # - MultipleVolumeRenderingVolumetricPresentationStateStorage
 # - OphthalmicOpticalCoherenceTomographyBscanVolumeAnalysisStorage
 # - OphthalmicOpticalCoherenceTomographyEnFaceImageStorage
@@ -1054,10 +1126,18 @@ Role127 = XRayRadiationDoseSRStorage\BOTH
 # - PerformedImagingAgentAdministrationSRStorage
 # - PlannedImagingAgentAdministrationSRStorage
 # - ProtocolApprovalStorage
+# - RoboticArmRadiationStorage
+# - RoboticRadiationRecordStorage
+# - RoutineScalpElectroencephalogramWaveformStorage
 # - RTPhysicianIntentStorage
+# - RTRadiationRecordSetStorage
+# - RTRadiationSalvageRecordStorage
 # - RTRadiationSetStorage
 # - RTSegmentAnnotationStorage
 # - SegmentedVolumeRenderingVolumetricPresentationStateStorage
+# - SleepElectroencephalogramWaveformStorage
+# - TomotherapeuticRadiationRecordStorage
+# - TomotherapeuticRadiationStorage
 # - VolumeRenderingVolumetricPresentationStateStorage
 #
 # - RETIRED_HardcopyColorImageStorage
index 3a1fa0011c3a24f69189532d6ab76ee4ea8bf121..45e6466ae52fe40b55a17bf8e3b9944a66c99849 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1993-2017, OFFIS e.V.
+ *  Copyright (C) 1993-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -28,7 +28,7 @@
 
 class DcmQueryRetrieveDatabaseHandle;
 class DcmQueryRetrieveOptions;
-class DcmQueryRetrieveCharacterSetOptions;
+struct DcmQueryRetrieveCharacterSetOptions;
 
 /** this class maintains the context information that is passed to the
  *  callback function called by DIMSE_findProvider.
@@ -45,12 +45,12 @@ public:
       DcmQueryRetrieveDatabaseHandle& handle,
       const DcmQueryRetrieveOptions& options,
       DIC_US priorStat,
-      const DcmQueryRetrieveCharacterSetOptions& characterSetOptions)
+      const DcmQueryRetrieveCharacterSetOptions& charSetOptions)
     : dbHandle(handle)
     , options_(options)
     , priorStatus(priorStat)
     , ourAETitle()
-    , characterSetOptions(characterSetOptions)
+    , characterSetOptions(charSetOptions)
     {
     }
 
index 9284d68b97daddaf7a9e56e157ea7ccbd5c20806..03ebfc1b44380d2c828672f104207e8d9da3a84b 100644 (file)
@@ -400,7 +400,7 @@ public:
 
 private:
 
-  friend class DcmQueryRetrieveCharacterSetOptions;
+  friend struct DcmQueryRetrieveCharacterSetOptions;
 
   const char* vendorForPeerAETitle(const char *peerAETitle) const;
 
index 586d3e050de1729eae57740c0c970e2a7a45b570..4b4b0bcb8647aab12ec33110278dad327af9d660 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1993-2018, OFFIS e.V.
+ *  Copyright (C) 1993-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -28,6 +28,7 @@
 #define INCLUDE_CCTYPE
 #define INCLUDE_CSTDARG
 #define INCLUDE_CSTRING
+#define INCLUDE_CLIMITS
 #include "dcmtk/ofstd/ofstdinc.h"
 #include "dcmtk/ofstd/ofcmdln.h"
 #include "dcmtk/ofstd/ofmap.h"
@@ -75,7 +76,7 @@ OFBool DcmQueryRetrieveCharacterSetOptions::parseOptions(const char* mnemonic, c
 {
     struct RAIIFree
     {
-        RAIIFree(char* ptr) : ptr(ptr) {}
+        RAIIFree(char* p) : ptr(p) {}
         ~RAIIFree() {free(ptr);}
         char* ptr;
     };
@@ -601,13 +602,13 @@ int DcmQueryRetrieveConfig::readAETable(FILE *cnffp, int *lineno)
       CNF_Config.AEEntries[noOfAEEntries - 1].StorageArea = parsevalues(&lineptr);
       CNF_Config.AEEntries[noOfAEEntries - 1].Access = parsevalues(&lineptr);
       CNF_Config.AEEntries[noOfAEEntries - 1].StorageQuota = parseQuota(&lineptr);
-      if ((CNF_Config.AEEntries[noOfAEEntries - 1].StorageQuota->maxStudies == 0) ||
-         (CNF_Config.AEEntries[noOfAEEntries - 1].StorageQuota->maxBytesPerStudy == 0))
-         error = 1;
-      else
-      {
-        CNF_Config.AEEntries[noOfAEEntries - 1].Peers = parsePeers(&lineptr, &CNF_Config.AEEntries[noOfAEEntries - 1].noOfPeers);
-        if (!CNF_Config.AEEntries[noOfAEEntries - 1].noOfPeers) error = 1;
+      CNF_Config.AEEntries[noOfAEEntries - 1].Peers = parsePeers(&lineptr, &CNF_Config.AEEntries[noOfAEEntries - 1].noOfPeers);
+
+      // check the validity of the storage quota and peers values before continuing
+      if (CNF_Config.AEEntries[noOfAEEntries - 1].StorageQuota->maxStudies == 0 ||
+         CNF_Config.AEEntries[noOfAEEntries - 1].StorageQuota->maxBytesPerStudy == 0 || 
+         CNF_Config.AEEntries[noOfAEEntries - 1].noOfPeers == 0) {
+          error = 1;
       }
    }
 
@@ -651,6 +652,12 @@ DcmQueryRetrieveConfigPeer *DcmQueryRetrieveConfig::parsePeers(char **valuehandl
    char *valueptr = *valuehandle;
 
    helpvalue = parsevalues(valuehandle);
+
+   if (!helpvalue) {
+      *peers = 0; // indicates error to caller
+      return NULL;
+   }
+
    if (!strcmp("ANY", helpvalue)) {     /* keyword ANY used */
       free(helpvalue);
       *peers = -1;
@@ -854,6 +861,11 @@ long DcmQueryRetrieveConfig::quota (const char *value)
    else return(-1L);
 
    number = atoi(value);
+
+   // check for overflow
+   if (number > 0 && factor > LONG_MAX / number)
+     return LONG_MAX;
+
    return(number * factor);
 }
 
index 1ef1ec4746fafcdf83ef67546a29d33d9e4e7bc4..60fdb4afba2b6f705691fe33941c4da0a322ca02 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1993-2018, OFFIS e.V.
+ *  Copyright (C) 1993-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -1680,33 +1680,33 @@ OFCondition DcmQueryRetrieveIndexDatabaseHandle::nextFindResponse (
         }
 
         if (isConversionNecessary(specificCharacterSet, *destinationCharacterSet)) {
-            OFCondition status = (*findResponseIdentifiers)->convertCharacterSet(
+            OFCondition charset_status = (*findResponseIdentifiers)->convertCharacterSet(
                 specificCharacterSet,
                 *destinationCharacterSet,
                 characterSetOptions.conversionFlags,
                 OFTrue);
-            if (status.bad()) {
+            if (charset_status.bad()) {
                 DCMQRDB_WARN("Converting response from character set \""
                     << characterSetName(specificCharacterSet)
                     << "\" to character set \""
                     << characterSetName(*destinationCharacterSet)
-                    << "\" failed, (error message: " << status.text() << ')');
+                    << "\" failed, (error message: " << charset_status.text() << ')');
                 if (fallbackCharacterSet && isConversionNecessary(specificCharacterSet, *fallbackCharacterSet)) {
                     DCMQRDB_INFO("Trying to convert response from character set \""
                         << characterSetName(specificCharacterSet)
                         << "\" to fall-back character set \""
                         << characterSetName(*fallbackCharacterSet) << "\" instead");
-                    status = (*findResponseIdentifiers)->convertCharacterSet(
+                    charset_status = (*findResponseIdentifiers)->convertCharacterSet(
                         specificCharacterSet,
                         *fallbackCharacterSet,
                         characterSetOptions.conversionFlags,
                         OFTrue);
-                    if (status.bad()) {
+                    if (charset_status.bad()) {
                         DCMQRDB_WARN("Converting response from character set \""
                             << characterSetName(specificCharacterSet)
                             << "\" to character set \""
                             << characterSetName(*fallbackCharacterSet)
-                            << "\" failed, (error message: " << status.text() << ')');
+                            << "\" failed, (error message: " << charset_status.text() << ')');
                     } else {
                         DCMQRDB_INFO("Successfully converted response from character set \""
                             << characterSetName(specificCharacterSet)
@@ -1784,7 +1784,7 @@ OFCondition DcmQueryRetrieveIndexDatabaseHandle::nextFindResponse (
 
     }
 
-    /**** If an error occured in Matching function
+    /**** If an error occurred in Matching function
     ****    return status is pending
     ***/
 
index 17fa30dc276ac2dc3fc3fef8229a555a6241afa1..e2b40431620b7f42f851515ae5df37a3eb2e51f7 100644 (file)
@@ -96,7 +96,7 @@ public:
      *               coordinate 0.
      *  @param frame frame to use. The first frame has number 0, the last
      *               frame is getNumberOfFrames()-1.
-     *  @return unscaled dose value for the pixel or 0 if an error occured.
+     *  @return unscaled dose value for the pixel or 0 if an error occurred.
      */
     virtual double getUnscaledDose(unsigned int x, unsigned int y, unsigned int frame = 0) const;
 
index f1c2ef3c381d478eb924f1c11008ae8bde6bd34a..2b7b6643d0cd6adaaa1f8f16bcba9959168e036d 100644 (file)
@@ -1,13 +1,14 @@
 /*
  *
  *  Copyright (C) 2008-2012, OFFIS e.V. and ICSMED AG, Oldenburg, Germany
- *  Copyright (C) 2013-2017, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2013-2019, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class DRTReferencedBeamSequenceInRTGeneralTreatmentRecordModule
  *
  *  Generated automatically from DICOM PS 3.3-2017e
  *  File created on 2017-12-05 09:30:54
+ *  Last modified on 2019-10-31 by Riesmeier
  *
  */
 
@@ -25,7 +26,7 @@ DRTReferencedBeamSequenceInRTGeneralTreatmentRecordModule::Item::Item(const OFBo
     AlternateBeamDoseType(DCM_AlternateBeamDoseType),
     BeamDeliveryDurationLimit(DCM_BeamDeliveryDurationLimit),
     BeamDose(DCM_BeamDose),
-    BeamDoseSpecificationPoint(DCM_BeamDoseSpecificationPoint),
+    BeamDoseSpecificationPoint(DCM_RETIRED_BeamDoseSpecificationPoint),
     BeamDoseType(DCM_BeamDoseType),
     BeamMeterset(DCM_BeamMeterset),
     ReferencedBeamNumber(DCM_ReferencedBeamNumber),
index 131cd05b575ceae58480c161315dad34d4775229..40b8757d58626fe513265cc591d6428b1e3c907b 100644 (file)
@@ -1,13 +1,14 @@
 /*
  *
  *  Copyright (C) 2008-2012, OFFIS e.V. and ICSMED AG, Oldenburg, Germany
- *  Copyright (C) 2013-2017, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2013-2019, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class DRTReferencedBeamSequenceInRTFractionSchemeModule
  *
  *  Generated automatically from DICOM PS 3.3-2017e
  *  File created on 2017-12-05 09:30:54
+ *  Last modified on 2019-10-31 by Riesmeier
  *
  */
 
@@ -25,7 +26,7 @@ DRTReferencedBeamSequenceInRTFractionSchemeModule::Item::Item(const OFBool empty
     AlternateBeamDoseType(DCM_AlternateBeamDoseType),
     BeamDeliveryDurationLimit(DCM_BeamDeliveryDurationLimit),
     BeamDose(DCM_BeamDose),
-    BeamDoseSpecificationPoint(DCM_BeamDoseSpecificationPoint),
+    BeamDoseSpecificationPoint(DCM_RETIRED_BeamDoseSpecificationPoint),
     BeamDoseType(DCM_BeamDoseType),
     BeamMeterset(DCM_BeamMeterset),
     ReferencedBeamNumber(DCM_ReferencedBeamNumber),
index 657a6881070c6a56b571da444a9a008b6ba87c1d..dcc5e3b4877f0fc1d12d308f560738757168a6fe 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *
  */
 
-
 #ifndef SEGDEF_H
 #define SEGDEF_H
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/ofstd/ofdefine.h"
 
 // definitions for DLL/shared library exports
index edd82e8e821c188d8659704d1416e057e7388af7..3e825da83b99adcde92953786cda47be6321ad48 100644 (file)
 #ifndef SEGDOC_H
 #define SEGDOC_H
 
-#include "dcmtk/config/osconfig.h"              // include OS configuration first
-#include "dcmtk/ofstd/ofvector.h"               // for OFVector
-#include "dcmtk/dcmiod/iodimage.h"              // common image IOD attribute access
-#include "dcmtk/dcmiod/iodmacro.h"
-#include "dcmtk/dcmiod/modimagepixel.h"
-#include "dcmtk/dcmiod/modsegmentationseries.h" // for segmentation series module
-#include "dcmtk/dcmiod/modenhequipment.h"       // for enhanced general equipment module
+#include "dcmtk/config/osconfig.h" // include OS configuration first
 
-#include "dcmtk/dcmiod/modmultiframefg.h"       // for multi-frame functional group module
-#include "dcmtk/dcmiod/modmultiframedimension.h"// for multi-frame dimension module
 #include "dcmtk/dcmdata/dcvrui.h"
-
-#include "dcmtk/dcmfg/fginterface.h"            // for multi-frame functional group interface
-#include "dcmtk/dcmfg/fgfracon.h"               // for frame content functional group macro
-
-#include "dcmtk/dcmseg/segtypes.h"              // for segmentation data types
+#include "dcmtk/dcmfg/concatenationcreator.h" // for writing concatenations
+#include "dcmtk/dcmfg/concatenationloader.h"  // for loading concatenations
+#include "dcmtk/dcmfg/fgfracon.h"             // for frame content functional group macro
+#include "dcmtk/dcmfg/fginterface.h"          // for multi-frame functional group interface
+#include "dcmtk/dcmiod/iodimage.h"            // common image IOD attribute access
+#include "dcmtk/dcmiod/iodmacro.h"
+#include "dcmtk/dcmiod/modenhequipment.h" // for enhanced general equipment module
+#include "dcmtk/dcmiod/modimagepixel.h"
+#include "dcmtk/dcmiod/modmultiframedimension.h" // for multi-frame dimension module
+#include "dcmtk/dcmiod/modmultiframefg.h"        // for multi-frame functional group module
+#include "dcmtk/dcmiod/modsegmentationseries.h"  // for segmentation series module
 #include "dcmtk/dcmseg/segdef.h"
-
+#include "dcmtk/dcmseg/segtypes.h" // for segmentation data types
+#include "dcmtk/ofstd/ofvector.h"  // for OFVector
 
 // Forward declarations
 class DcmSegment;
@@ -48,638 +47,632 @@ class FGDerivationImage;
 
 /** Class representing an object of the "Segmentation SOP Class".
  */
-class DCMTK_DCMSEG_EXPORT DcmSegmentation
-: public DcmIODImage<IODImagePixelModule<Uint8> >
+class DCMTK_DCMSEG_EXPORT DcmSegmentation : public DcmIODImage<IODImagePixelModule<Uint8> >
 {
 
 public:
-
-  // -------------------- destruction -------------------------------
-
-  /** Destructor, frees memory
-   */
-  virtual ~DcmSegmentation();
-
-  // -------------------- loading and saving ---------------------
-
-  /** Static method to load a Segmentation object from a file.
-   *  The memory of the resulting Segmentation object has to be freed by the
-   *  caller.
-   *  @param  filename The file to read from
-   *  @param  segmentation  The resulting segmentation object. NULL if dataset
-   *          could not be read successfully.
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  static OFCondition loadFile(const OFString& filename,
-                              DcmSegmentation*& segmentation);
-
-  /** Static method to load a Segmentation object from a dataset object.
-   *  The memory of the resulting Segmentation object has to be freed by the
-   *  caller.
-   *  @param  dataset The dataset to read from
-   *  @param  segmentation  The resulting segmentation object. NULL if dataset
-   *          could not be read successfully.
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  static OFCondition loadDataset(DcmDataset& dataset,
-                                 DcmSegmentation*& segmentation);
-
-  /** Save current object to given filename
-   *  @param  filename The file to write to
-   *  @param  writeXfer The transfer syntax to be used
-   *  @return EC_Normal if writing was successful, error otherwise.
-   */
-  OFCondition saveFile(const OFString& filename,
-                       const E_TransferSyntax writeXfer = EXS_LittleEndianExplicit);
-
-  /** Write current object to given item
-   *  @param  dataset The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise.
-   */
-  OFCondition writeDataset(DcmItem& dataset);
-
-  /** If enabled, functional group structure is checked before actual writing
-   *  is performed in the write() method. Checking might be time consuming
-   *  on functional groups with many frames, though disabling might result in
-   *  invalid functional group structures. Disabling should only be done if the
-   *  user knows that the functional groups are valid, wants to to adapt the
-   *  functional groups manually after calling write() or knows what he's doing
-   *  otherwise.<br>
-   *  Per default, checking is enabled.
-   *  @param  doCheck If OFTrue, checking will be performed. If OFFalse,
-   *          no checks are performed.
-   */
-  virtual void setCheckFGOnWrite(const OFBool doCheck);
-
-  /** Returns whether functional group structure is checked before actual
-   *  writing is performed in the write() method.
-   *  @return OFTrue if checking is performed, OFFalse otherwise
-   */
-  virtual OFBool getCheckFGOnWrite();
-
-
-  // -------------------- creation ---------------------
-
-  /** Factory method to create a binary segmentation object from the minimal
-   *  set of information required. The actual segments and the frame data is
-   *  added separately.
-   *  The memory of the resulting Segmentation object has to be freed by the
-   *  caller.
-   *  @param  segmentation The resulting segmentation object if provided data is
-   *          valid. Otherwise NULL is returned.
-   *  @param  rows Number of rows of segmentation frame data
-   *  @param  columns Number of rows of segmentation frame data
-   *  @param  equipmentInfo Equipment that is responsible for creating the
-   *           segmentation
-   *  @param  contentIdentification Basic content identification information
-   *  @return EC_Normal if creation was successful, error otherwise
-   */
-  static OFCondition createBinarySegmentation(DcmSegmentation*& segmentation,
-                                              const Uint16 rows,
-                                              const Uint16 columns,
-                                              const IODGeneralEquipmentModule::EquipmentInfo& equipmentInfo,
-                                              const ContentIdentificationMacro& contentIdentification);
-
-  /** Factory method to create a fractional segmentation object from the minimal
-   *  set of information required. The actual segments and the frame data is
-   *  added separately.
-   *  The memory of the resulting Segmentation object has to be freed by the
-   *  caller.
-   *  @param  segmentation The resulting segmentation object if provided data is
-   *          valid. Otherwise NULL is returned.
-   *  @param  rows Number of rows of segmentation frame data
-   *  @param  columns Number of rows of segmentation frame data
-   *  @param  fractType Either probability (SFT_PROBABILITY) or
-   *          occupancy (SFT_OCCUPANCY)
-   *  @param  maxFractionalValue The value inside the frame data of this
-   *          segmentation that represents 100% occupancy/probability
-   *  @param  equipmentInfo Equipment that is responsible for creating the
-   *          segmentation
-   *  @param  contentIdentification Basic content identification information
-   *  @return EC_Normal if creation was successful, error otherwise
-   */
-  static OFCondition createFractionalSegmentation(DcmSegmentation*& segmentation,
-                                                  const Uint16 rows,
-                                                  const Uint16 columns,
-                                                  const DcmSegTypes::E_SegmentationFractionalType fractType,
-                                                  const Uint16& maxFractionalValue,
-                                                  const IODGeneralEquipmentModule::EquipmentInfo& equipmentInfo,
-                                                  const ContentIdentificationMacro& contentIdentification);
-
-  /** Helps to create a valid Derivation Image Functional Group Macro
-   *  The memory of the resulting functional group object has to be freed by the
-   *  caller.
-   *  @param derivationImages to image SOP instances
-   *  @param derivationDescription Free text describing how the derivation was
-   *         achieved.
-   *  @return The created functional group, or NULL if not successful
-   */
-  static FGDerivationImage* createDerivationImageFG(const OFVector<ImageSOPInstanceReferenceMacro>& derivationImages,
-                                                    const OFString& derivationDescription);
-
-  // -------------------- access ---------------------
-
-  /** Get number of frames, based on the number of items in the shared
-   *  functional functional groups sequence (i.e.\ the attribute Number of
-   *  Frames) is not trusted).
-   *  @return The number of frames handled by this object
-   */
-  size_t getNumberOfFrames();
-
-  /** Get Segmentation Type
-   *  @return Type of the segmentation, as defined by DcmSegTypes::E_SegmentationType
-   */
-  DcmSegTypes::E_SegmentationType getSegmentationType()
-  {
-    return this->m_SegmentationType;
-  }
-
-  /** Get Fractional Segmentation Type
-   *  @return Type of the segmentation, as defined by
-   *  DcmSegTypes::E_SegmentationFractionalTypes (returns SFT_UNKNOWN if not
-   *  fractional at all)
-   */
-  DcmSegTypes::E_SegmentationFractionalType getSegmentationFractionalType()
-  {
-    return this->m_SegmentationFractionalType;
-  }
-
-  /** Get the Number of Segments
-   *  @return The number of segments handled by this object
-   */
-  size_t getNumberOfSegments();
-
-  /** Perform some basic checking. This method is also invoked when
-   *  writing the object to a DICOM dataset or file.
-   *  @param  checkFGStructure If OFTrue (default), structure of functional
-   *          groups is checked, too.
-   *  @return OFTrue, if no errors were found, OFFalse otherwise.
-   */
-  virtual OFBool check(const OFBool checkFGStructure = OFTrue);
-
-  /** Get access to functional groups. This is meant for reading data from
-   *  functional groups that are not actively managed, i.e.\ made accessible by
-   *  DcmSegmentation. In rare cases, however, it makes sense to access it
-   *  for writing too, e.g.\ in order to add Stacks; use with care!
-   *  @return Reference to the functional groups
-   */
-  virtual FGInterface& getFunctionalGroups();
-
-  /** Get General Equipment Module
-   *  @return General Equipment Module
-   */
-  virtual IODGeneralEquipmentModule& getEquipment();
-
-  /** Get Segmentation Series Module
-   *  @return Segmentation Series Module
-   */
-  virtual IODSegmentationSeriesModule& getSegmentationSeriesModule();
-
-  /** Get modality (overwrite from DcmIODCommon. We always return "SEG" here)
-   *  @param  value  Reference to variable in which the value should be stored
-   *  @param  pos    Index of the value to get. Not evaluated (here for
-   *          consistency with other setter functions).
-   *  @return status, EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getModality(OFString &value,
-                                  const signed long pos = 0) const;
-
-  /** Get segment by providing the logical segment number
-   *  @param  segmentNumber The logical segment number
-   *  @return The segment if segment number is valid, NULL otherwise
-   */
-  virtual DcmSegment* getSegment(const unsigned int segmentNumber);
-
-  /** Get logical segment number by providing a pointer to a given segment
-   *  @param  segment The segment to find the logical segment number for
-   *  @param  segmentNumber The segment number. 0 if segment could not be found.
-   *  @return OFTrue if segment could be found, OFFalse otherwise.
-   */
-  virtual OFBool getSegmentNumber(const DcmSegment* segment,
-                                  unsigned int& segmentNumber);
-
-  /** Reference to the Performed Procedure Step that led to the creation of this
-   *  segmentation object. This is required if this object is created in an MPPS
-   *  or GPPS workflow.
-   *  @return Reference to the referenced PPS object
-   */
-  virtual SOPInstanceReferenceMacro& getReferencedPPS();
-
-  /** Get (const) frame data of a specific frame
-   *  @param  frameNo The number of the frame to get (starting with 0)
-   *  @return The frame requested or NULL if not existing
-   */
-  virtual const DcmIODTypes::Frame* getFrame(const size_t& frameNo);
-
-  /** Get the frame numbers that belong to a specific segment number
-   *  @param  segmentNumber The segment to search frames for
-   *  @param  frameNumbers  The frame numbers belonging to that segment
-   */
-  virtual void getFramesForSegment(const size_t& segmentNumber,
-                                   OFVector<size_t>& frameNumbers);
-
-  // -------------------- modification ---------------------
-
-  /** Add segment to segmentation object
-   *  @param  seg The segment that should be added
-   *  @param  segmentNumber The logical segment number that was assigned for
-   *          this segment. Contains 0 if adding failed.
-   *  @return EC_Normal if adding was successful, error otherwise
-   */
-  virtual OFCondition addSegment(DcmSegment* seg,
-                                 Uint16& segmentNumber);
-
-  /** Add a functional group for all frames
-   *  @param  group The group to be added as shared functional group. The
-   *  @return EC_Normal if adding was successful, error otherwise
-   */
-  virtual OFCondition addForAllFrames(const FGBase& group);
-
-  /** Add frame to segmentation object
-   *  @param  pixData Pixel data to be added. Length must be rows*columns bytes.
-   *          For binary segmentations (bit depth i.e.\ Bits
-   *          Allocated/Stored=1), each byte equal to 0 will be interpreted as
-   *          "not set", while every other value is interpreted as "set". For
-   *          fractional segmentations the full byte is copied as is.
-   *  @param  segmentNumber The logical segment number (>=1) this frame refers to.
-   *          The segment identified by the segmentNumber must already exist.
-   *  @param  perFrameInformation The functional groups that identify this frame (i.e.
-   *          which are planned to be not common for all other frames). The
-   *          functional groups are copied, so ownership of each group stays
-   *          with the caller no matter what the method returns.
-   *  @return EC_Normal if adding was successful, error otherwise
-   */
-  virtual OFCondition addFrame(Uint8* pixData,
-                               const Uint16 segmentNumber,
-                               const OFVector<FGBase*>& perFrameInformation);
-
-  /** Return reference to content content identification of this segmentation object
-   *  @return Reference to content identification data
-   */
-  virtual ContentIdentificationMacro& getContentIdentification();
-
-  /** Return reference to multi-fame dimension module
-   *  @return Reference to multi-frame dimension module
-   */
-  virtual IODMultiframeDimensionModule& getDimensions();
-
-  /** Set lossy compression flag of the segmentation object to "01". If one of the
-   *  source images of this segmentation has undergone lossy compression then
-   *  this function should be called.
-   *  @param  ratios Compression ratios (separated by backslash) of the applied
-   *          lossy compression steps. Only one value (and no backslash) if only
-   *          one step was performed.
-   *  @param  methods Methods (separated by backslash) of the applied
-   *          lossy compression steps. Only one value (and no backslash) if only
-   *          one step was performed.
-   *  @param  checkValues If OFTrue, the data provided is checked for validity
-   *  @return EC_Normal if lossy compression info could be set, error code otherwise
-   */
-  virtual OFCondition setLossyImageCompressionFlag(const OFString& ratios,
-                                                   const OFString& methods,
-                                                   const OFBool checkValues = OFTrue);
-
-  /** Set equipment info for this segmentation object
-   *  @param  equipmentInfo  The description of the equipment used to create
-   *          this segmentation
-   *  @param  checkValue If OFTrue, the data provided is checked for validity
-   *  @return EC_Normal if equipment information could be set successfully, error otherwise
-   */
-  virtual OFCondition setEquipmentInfo(const IODGeneralEquipmentModule::EquipmentInfo& equipmentInfo,
-                                       const OFBool checkValue = OFTrue);
-
-  /** Set content identification info for this segmentation object
-   *  @param  contentIdentification  The content identification of this segmentation
-   *  @param  checkValue If OFTrue, the data provided is checked for validity
-   *          (as possible)
-   *  @return EC_Normal if content identification could be set correctly, OFFalse otherwise
-   */
-  virtual OFCondition setContentIdentification(const ContentIdentificationMacro& contentIdentification,
-                                               const OFBool checkValue = OFTrue);
-
-  /** Import Patient, Study, and Frame of Reference level information from the
-   *  given item. The method does only import Frame of Reference if Frame of
-   *  Reference (FoR) UID is found in the image (and no error is reported if not).
-   *  The reason is that if the source images of the segmentation do have an
-   *  FoR, the segmentation object must have the same one, so we must import it.
-   *  If the images do not have an FoR, we must not try at all importing it.
-   *  If the log stream is set and valid the, the reason for any error might be
-   *  obtained from the error/warning output.
-   *  @param  dataset Reference to DICOM dataset from which the document
-   *          should be read
-   *  @param  takeOverCharset If OFTrue (default), Specific Character Set is
-   *                          taken over from imported dataset. If it's not
-   *                          present or empty (invalid), the attribute will
-   *                          not be present in this class either.
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition importFromSourceImage(DcmItem& dataset,
-                                            const OFBool takeOverCharset = OFTrue);
-
-  /** Import Patient, Study, and Frame of Reference level information from the
-   *  given item. The method does only import Frame of Reference if Frame of
-   *  Reference UID is found in the image (and no error is reported if not).
-   *  The reason is that if the source images of the segmentation do have an
-   *  FoR, the segmentation object must have the same one, so we must import it.
-   *  If the images do not have an FoR, we must not try at all importing it.
-   *  The current content of this object is not deleted before reading.
-   *  If the log stream is set and valid the, the reason for any error might be
-   *  obtained from the error/warning output.
-   *  @param  filename Reference to DICOM dataset from which the document
-   *          should be read
-   *  @param  takeOverCharset If OFTrue (default), Specific Character Set is
-   *                          taken over from imported dataset. If it's not
-   *                          present or empty (invalid), the attribute will
-   *                          not be present in this class either.
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition importFromSourceImage(const OFString& filename,
-                                            const OFBool takeOverCharset = OFTrue);
+    // -------------------- destruction -------------------------------
+
+    /** Destructor, frees memory
+     */
+    virtual ~DcmSegmentation();
+
+    // -------------------- loading and saving ---------------------
+
+    /** Static method to load a Segmentation object from a file.
+     *  The memory of the resulting Segmentation object has to be freed by the
+     *  caller.
+     *  @param  filename The file to read from
+     *  @param  segmentation  The resulting segmentation object. NULL if dataset
+     *          could not be read successfully.
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    static OFCondition loadFile(const OFString& filename, DcmSegmentation*& segmentation);
+
+    /** Static method to load a Segmentation object from a dataset object.
+     *  The memory of the resulting Segmentation object has to be freed by the
+     *  caller.
+     *  @param  dataset The dataset to read from
+     *  @param  segmentation  The resulting segmentation object. NULL if dataset
+     *          could not be read successfully.
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    static OFCondition loadDataset(DcmDataset& dataset, DcmSegmentation*& segmentation);
+
+    /** Static method to load a concatenation of a DICOM Segmentation instance
+     *  into a DcmSegmentation object.
+     *  @param  cl The ConcatenationLoader instance to be used. Must be configured
+     *          so that load() can be called.
+     *  @param  concatenationUID The Concatenation UID identifying the Concatenation
+     *          within the Concatenations know to ConcatenationLoader cl.
+     *  @param  segmentation The resulting Segmentation object, if loading was successful
+     *  @return EC_Normal if loading was successful, error otherwise
+     */
+    static OFCondition
+    loadConcatenation(ConcatenationLoader& cl, const OFString& concatenationUID, DcmSegmentation*& segmentation);
+
+    /** Save current object to given filename
+     *  @param  filename The file to write to
+     *  @param  writeXfer The transfer syntax to be used
+     *  @return EC_Normal if writing was successful, error otherwise.
+     */
+    OFCondition saveFile(const OFString& filename, const E_TransferSyntax writeXfer = EXS_LittleEndianExplicit);
+
+    /** Write current object to given item
+     *  @param  dataset The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise.
+     */
+    OFCondition writeDataset(DcmItem& dataset);
+
+    /** Write current object to a Concatenation.
+     *  @param  cc The Concatenation Creator object to be used. Must be configured
+     *          so that writeNextInstance() is ready to be called.
+     *  @return EC_Normal if writing was successful, error otherwise.
+     */
+    OFCondition writeConcatenation(ConcatenationCreator& cc);
+
+    /** If enabled, functional group structure is checked before actual writing
+     *  is performed in the write() method. Checking might be time consuming
+     *  on functional groups with many frames, though disabling might result in
+     *  invalid functional group structures. Disabling should only be done if the
+     *  user knows that the functional groups are valid, wants to to adapt the
+     *  functional groups manually after calling write() or knows what he's doing
+     *  otherwise.<br>
+     *  Per default, checking is enabled.
+     *  @param  doCheck If OFTrue, checking will be performed. If OFFalse,
+     *          no checks are performed.
+     */
+    virtual void setCheckFGOnWrite(const OFBool doCheck);
+
+    /** Returns whether functional group structure is checked before actual
+     *  writing is performed in the write() method.
+     *  @return OFTrue if checking is performed, OFFalse otherwise
+     */
+    virtual OFBool getCheckFGOnWrite();
+
+    // -------------------- creation ---------------------
+
+    /** Factory method to create a binary segmentation object from the minimal
+     *  set of information required. The actual segments and the frame data is
+     *  added separately.
+     *  The memory of the resulting Segmentation object has to be freed by the
+     *  caller.
+     *  @param  segmentation The resulting segmentation object if provided data is
+     *          valid. Otherwise NULL is returned.
+     *  @param  rows Number of rows of segmentation frame data
+     *  @param  columns Number of rows of segmentation frame data
+     *  @param  equipmentInfo Equipment that is responsible for creating the
+     *          segmentation. All attributes in equipmentInfo must have
+     *          non-empty values.
+     *  @param  contentIdentification Basic content identification information
+     *  @return EC_Normal if creation was successful, error otherwise
+     */
+    static OFCondition createBinarySegmentation(DcmSegmentation*& segmentation,
+                                                const Uint16 rows,
+                                                const Uint16 columns,
+                                                const IODGeneralEquipmentModule::EquipmentInfo& equipmentInfo,
+                                                const ContentIdentificationMacro& contentIdentification);
+
+    /** Factory method to create a fractional segmentation object from the minimal
+     *  set of information required. The actual segments and the frame data is
+     *  added separately.
+     *  The memory of the resulting Segmentation object has to be freed by the
+     *  caller.
+     *  @param  segmentation The resulting segmentation object if provided data is
+     *          valid. Otherwise NULL is returned.
+     *  @param  rows Number of rows of segmentation frame data
+     *  @param  columns Number of rows of segmentation frame data
+     *  @param  fractType Either probability (SFT_PROBABILITY) or
+     *          occupancy (SFT_OCCUPANCY)
+     *  @param  maxFractionalValue The value inside the frame data of this
+     *          segmentation that represents 100% occupancy/probability
+     *  @param  equipmentInfo Equipment that is responsible for creating the
+     *          segmentation. All attributes in equipmentInfo must have
+     *          non-empty values.
+     *  @param  contentIdentification Basic content identification information
+     *  @return EC_Normal if creation was successful, error otherwise
+     */
+    static OFCondition createFractionalSegmentation(DcmSegmentation*& segmentation,
+                                                    const Uint16 rows,
+                                                    const Uint16 columns,
+                                                    const DcmSegTypes::E_SegmentationFractionalType fractType,
+                                                    const Uint16& maxFractionalValue,
+                                                    const IODGeneralEquipmentModule::EquipmentInfo& equipmentInfo,
+                                                    const ContentIdentificationMacro& contentIdentification);
+
+    /** Helps to create a valid Derivation Image Functional Group Macro
+     *  The memory of the resulting functional group object has to be freed by the
+     *  caller.
+     *  @param derivationImages to image SOP instances
+     *  @param derivationDescription Free text describing how the derivation was
+     *         achieved.
+     *  @return The created functional group, or NULL if not successful
+     */
+    static FGDerivationImage* createDerivationImageFG(const OFVector<ImageSOPInstanceReferenceMacro>& derivationImages,
+                                                      const OFString& derivationDescription);
+
+    // -------------------- access ---------------------
+
+    /** Get number of frames, based on the number of items in the shared
+     *  functional functional groups sequence (i.e.\ the attribute Number of
+     *  Frames) is not trusted).
+     *  @return The number of frames handled by this object
+     */
+    size_t getNumberOfFrames();
+
+    /** Get Segmentation Type
+     *  @return Type of the segmentation, as defined by DcmSegTypes::E_SegmentationType
+     */
+    DcmSegTypes::E_SegmentationType getSegmentationType()
+    {
+        return this->m_SegmentationType;
+    }
+
+    /** Get Fractional Segmentation Type
+     *  @return Type of the segmentation, as defined by
+     *  DcmSegTypes::E_SegmentationFractionalTypes (returns SFT_UNKNOWN if not
+     *  fractional at all)
+     */
+    DcmSegTypes::E_SegmentationFractionalType getSegmentationFractionalType()
+    {
+        return this->m_SegmentationFractionalType;
+    }
+
+    /** Get the Number of Segments
+     *  @return The number of segments handled by this object
+     */
+    size_t getNumberOfSegments();
+
+    /** Perform some basic checking. This method is also invoked when
+     *  writing the object to a DICOM dataset or file.
+     *  @param  checkFGStructure If OFTrue (default), structure of functional
+     *          groups is checked, too.
+     *  @return OFTrue, if no errors were found, OFFalse otherwise.
+     */
+    virtual OFBool check(const OFBool checkFGStructure = OFTrue);
+
+    /** Get access to functional groups. This is meant for reading data from
+     *  functional groups that are not actively managed, i.e.\ made accessible by
+     *  DcmSegmentation. In rare cases, however, it makes sense to access it
+     *  for writing too, e.g.\ in order to add Stacks; use with care!
+     *  @return Reference to the functional groups
+     */
+    virtual FGInterface& getFunctionalGroups();
+
+    /** Get reference t Concatenation information
+     *  @return Reference to ConcatenationInfo object
+     */
+    virtual IODMultiFrameFGModule::ConcatenationInfo& getConcatenationInfo();
+
+    /** Get General Equipment Module
+     *  @return General Equipment Module
+     */
+    virtual IODGeneralEquipmentModule& getEquipment();
+
+    /** Get Segmentation Series Module
+     *  @return Segmentation Series Module
+     */
+    virtual IODSegmentationSeriesModule& getSegmentationSeriesModule();
+
+    /** Get modality (overwrite from DcmIODCommon. We always return "SEG" here)
+     *  @param  value  Reference to variable in which the value should be stored
+     *  @param  pos    Index of the value to get. Not evaluated (here for
+     *          consistency with other setter functions).
+     *  @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getModality(OFString& value, const signed long pos = 0) const;
+
+    /** Get segment by providing the logical segment number
+     *  @param  segmentNumber The logical segment number
+     *  @return The segment if segment number is valid, NULL otherwise
+     */
+    virtual DcmSegment* getSegment(const unsigned int segmentNumber);
+
+    /** Get logical segment number by providing a pointer to a given segment
+     *  @param  segment The segment to find the logical segment number for
+     *  @param  segmentNumber The segment number. 0 if segment could not be found.
+     *  @return OFTrue if segment could be found, OFFalse otherwise.
+     */
+    virtual OFBool getSegmentNumber(const DcmSegment* segment, unsigned int& segmentNumber);
+
+    /** Reference to the Performed Procedure Step that led to the creation of this
+     *  segmentation object. This is required if this object is created in an MPPS
+     *  or GPPS workflow.
+     *  @return Reference to the referenced PPS object
+     */
+    virtual SOPInstanceReferenceMacro& getReferencedPPS();
+
+    /** Get (const) frame data of a specific frame
+     *  @param  frameNo The number of the frame to get (starting with 0)
+     *  @return The frame requested or NULL if not existing
+     */
+    virtual const DcmIODTypes::Frame* getFrame(const size_t& frameNo);
+
+    /** Get the frame numbers that belong to a specific segment number
+     *  @param  segmentNumber The segment to search frames for
+     *  @param  frameNumbers  The frame numbers belonging to that segment
+     */
+    virtual void getFramesForSegment(const size_t& segmentNumber, OFVector<size_t>& frameNumbers);
+
+    // -------------------- modification ---------------------
+
+    /** Add segment to segmentation object
+     *  @param  seg The segment that should be added
+     *  @param  segmentNumber The logical segment number that was assigned for
+     *          this segment. Contains 0 if adding failed.
+     *  @return EC_Normal if adding was successful, error otherwise
+     */
+    virtual OFCondition addSegment(DcmSegment* seg, Uint16& segmentNumber);
+
+    /** Add a functional group for all frames
+     *  @param  group The group to be added as shared functional group. The
+     *  @return EC_Normal if adding was successful, error otherwise
+     */
+    virtual OFCondition addForAllFrames(const FGBase& group);
+
+    /** Add frame to segmentation object
+     *  @param  pixData Pixel data to be added. Length must be rows*columns bytes.
+     *          For binary segmentations (bit depth i.e.\ Bits
+     *          Allocated/Stored=1), each byte equal to 0 will be interpreted as
+     *          "not set", while every other value is interpreted as "set". For
+     *          fractional segmentations the full byte is copied as is.
+     *  @param  segmentNumber The logical segment number (>=1) this frame refers to.
+     *          The segment identified by the segmentNumber must already exist.
+     *  @param  perFrameInformation The functional groups that identify this frame (i.e.
+     *          which are planned to be not common for all other frames). The
+     *          functional groups are copied, so ownership of each group stays
+     *          with the caller no matter what the method returns.
+     *  @return EC_Normal if adding was successful, error otherwise
+     */
+    virtual OFCondition
+    addFrame(Uint8* pixData, const Uint16 segmentNumber, const OFVector<FGBase*>& perFrameInformation);
+
+    /** Return reference to content content identification of this segmentation object
+     *  @return Reference to content identification data
+     */
+    virtual ContentIdentificationMacro& getContentIdentification();
+
+    /** Return reference to multi-fame dimension module
+     *  @return Reference to multi-frame dimension module
+     */
+    virtual IODMultiframeDimensionModule& getDimensions();
+
+    /** Set lossy compression flag of the segmentation object to "01". If one of the
+     *  source images of this segmentation has undergone lossy compression then
+     *  this function should be called.
+     *  @param  ratios Compression ratios (separated by backslash) of the applied
+     *          lossy compression steps. Only one value (and no backslash) if only
+     *          one step was performed.
+     *  @param  methods Methods (separated by backslash) of the applied
+     *          lossy compression steps. Only one value (and no backslash) if only
+     *          one step was performed.
+     *  @param  checkValues If OFTrue, the data provided is checked for validity
+     *  @return EC_Normal if lossy compression info could be set, error code otherwise
+     */
+    virtual OFCondition
+    setLossyImageCompressionFlag(const OFString& ratios, const OFString& methods, const OFBool checkValues = OFTrue);
+
+    /** Set equipment info for this segmentation object
+     *  @param  equipmentInfo  The description of the equipment used to create
+     *          this segmentation
+     *  @param  checkValue If OFTrue, the data provided is checked for validity
+     *  @return EC_Normal if equipment information could be set successfully, error otherwise
+     */
+    virtual OFCondition setEquipmentInfo(const IODGeneralEquipmentModule::EquipmentInfo& equipmentInfo,
+                                         const OFBool checkValue = OFTrue);
+
+    /** Set content identification info for this segmentation object
+     *  @param  contentIdentification  The content identification of this segmentation
+     *  @param  checkValue If OFTrue, the data provided is checked for validity
+     *          (as possible)
+     *  @return EC_Normal if content identification could be set correctly, OFFalse otherwise
+     */
+    virtual OFCondition setContentIdentification(const ContentIdentificationMacro& contentIdentification,
+                                                 const OFBool checkValue = OFTrue);
+
+    /** Import Patient, Study, and Frame of Reference level information from the
+     *  given item. The method does only import Frame of Reference if Frame of
+     *  Reference (FoR) UID is found in the image (and no error is reported if not).
+     *  The reason is that if the source images of the segmentation do have an
+     *  FoR, the segmentation object must have the same one, so we must import it.
+     *  If the images do not have an FoR, we must not try at all importing it.
+     *  If the log stream is set and valid the, the reason for any error might be
+     *  obtained from the error/warning output.
+     *  @param  dataset Reference to DICOM dataset from which the document
+     *          should be read
+     *  @param  takeOverCharset If OFTrue (default), Specific Character Set is
+     *                          taken over from imported dataset. If it's not
+     *                          present or empty (invalid), the attribute will
+     *                          not be present in this class either.
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition importFromSourceImage(DcmItem& dataset, const OFBool takeOverCharset = OFTrue);
+
+    /** Import Patient, Study, and Frame of Reference level information from the
+     *  given item. The method does only import Frame of Reference if Frame of
+     *  Reference UID is found in the image (and no error is reported if not).
+     *  The reason is that if the source images of the segmentation do have an
+     *  FoR, the segmentation object must have the same one, so we must import it.
+     *  If the images do not have an FoR, we must not try at all importing it.
+     *  The current content of this object is not deleted before reading.
+     *  If the log stream is set and valid the, the reason for any error might be
+     *  obtained from the error/warning output.
+     *  @param  filename Reference to DICOM dataset from which the document
+     *          should be read
+     *  @param  takeOverCharset If OFTrue (default), Specific Character Set is
+     *                          taken over from imported dataset. If it's not
+     *                          present or empty (invalid), the attribute will
+     *                          not be present in this class either.
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition importFromSourceImage(const OFString& filename, const OFBool takeOverCharset = OFTrue);
 
 protected:
-
-  /** Protected default constructor. Library users should the factory create..()
-   *  method in order to create an object from scratch
-   */
-  DcmSegmentation();
-
-  /** Overwrites DcmIODImage::read()
-   *  @param  dataset The dataset to read from
-   *  @return EC_Normal if reading succeeded, error otherwise
-   */
-  OFCondition read(DcmItem &dataset);
-
-  /** Overwrites DcmIODImage::write()
-   *  @param  dataset The dataset to write to
-   *  @return EC_Normal if writing succeeded, error otherwise
-   */
-  OFCondition write(DcmItem &dataset);
-
-  /** Create those data structures common for binary and fractional
-   *  segmentations
-   *  @param  segmentation The segmentation object created
-   *  @param  rows The number of rows for the segmentation
-   *  @param  columns The number of columns for the segmentation
-   *  @param  equipmentInfo Equipment information
-   *  @param  contentIdentification Content meta information
-   *  @return EC_Normal if creation was successful, error otherwise
-   */
-  static OFCondition createCommon(DcmSegmentation*& segmentation,
-                                  const Uint16 rows,
-                                  const Uint16 columns,
-                                  const IODGeneralEquipmentModule::EquipmentInfo& equipmentInfo,
-                                  const ContentIdentificationMacro& contentIdentification);
-
-  /** Hide same function from IODImage since do not want the user to access
-  *  the image pixel module manually.
-  *  @return The Image Pixel Module
-  */
-  virtual IODImagePixelModule<Uint8>& getImagePixel();
-
-  /** Initialize IOD rules
-   */
-  virtual void initIODRules();
-
-  /** Read segments from given item
-   *  @param  item The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition readSegments(DcmItem& item);
-
-  /** Write fractional frames to given item
-   *  @param  dataset The item to write to, usually main dataset level
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition writeFractionalFrames(DcmItem& dataset);
-
-  /** Write binary frames to given item
-   *  @param  dataset The item to write to, usually main dataset level
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition writeBinaryFrames(DcmItem& dataset);
-
-
-  /** Write Segmentation Image Module
-   *  @param dataset The item to write to, usually main dataset level
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition writeSegmentationImageModule(DcmItem& dataset);
-
-  /** Write Segments
-   *  @param item The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition writeSegments(DcmItem& item);
-
-  /** Write Multi-Frame Functional Groups
-   *  @param dataset The item to write to, usually main dataset level
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition writeMultiFrameFunctionalGroupsModule(DcmItem& dataset);
-
-  /** Write Multi-Frame Dimension Module
-   *  @param dataset The item to write to, usually main dataset level
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition writeMultiFrameDimensionModule(DcmItem& dataset);
-
-  /** Read frames
-   *  @param  dataset Item to read from, usually main dataset level
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition readFrames(DcmItem& dataset);
-
-  /** Get Image Pixel module attributes and perform some basic checking
-   *  @param  dataset Item to read from, usually main dataset level
-   *  @param  allocated Bits Allocated
-   *  @param  stored Bits Stored
-   *  @param  high High Bit
-   *  @param  spp Samples Per Pixel
-   *  @param  pixelRep Pixel Representation
-   *  @param  rows Rows
-   *  @param  cols Columns
-   *  @param  numberOfFrames The number of frames (as set in the dataset)
-   *  @param  colorModel The color model used
-   *  @return EC_Normal if reading/checking was successful, error otherwise
-   */
-  virtual OFCondition getAndCheckImagePixelAttributes(DcmItem& dataset,
-                                                      Uint16& allocated,
-                                                      Uint16& stored,
-                                                      Uint16& high,
-                                                      Uint16& spp,
-                                                      Uint16& pixelRep,
-                                                      Uint16& rows,
-                                                      Uint16& cols,
-                                                      Uint16& numberOfFrames,
-                                                      OFString& colorModel);
-
-  /** Extracts Frame structures from the given pixel data element. Only
-   *  applicable for binary segmentations. Within the pixel data element, all
-   *  frames are packed next to each other, with the end of one frame and the
-   *  beginning of the next frame packed bit by bit next to each other. The
-   *  resulting Frames are a bit-by-bit copy of their original counterpart.
-   *  However, their first bit is aligned to the first bit/byte in the Frame,
-   *  and the unused bits in the last byte (if any) are zeroed out.
-   *  @param  pixData The pixel data to read from
-   *  @param  numFrames The number of frames to read
-   *  @param  bitsPerFrame The number of bits per frame (usually rows * columns)
-   *  @param  results The resulting frames. Memory for the frames is allocated
-   *          by the method, so the Vector can/should be empty before calling.
-   *  @result Return EC_Normal on success, error otherwise
-   */
-  virtual OFCondition extractFrames(Uint8* pixData,
-                                   const size_t numFrames,
-                                   const size_t bitsPerFrame,
-                                   OFVector< DcmIODTypes::Frame* >& results);
-
-  /** This is the counterpart to the extractFrames() function. It takes a number
-   *  of frames that are in binary segmentation format (i.e. "bit-packed") and
-   *  concatenates them together so the resulting memory block fits the Pixel
-   *  Data format for binary segmentations. Thus method ensure that frames
-   *  are aligned bit for bit concatenated to each other with only (if
-   *  applicable) having unused bits after the last frame.
-   *  @param frames The source frames
-   *  @param pixData The pixel data element data to be filled. Size must be
-   *         at least bitsPerFrame * number of frames.
-   *  @param bitsPerFrame Bits required per frame, usually rows * columns
-   */
-  virtual void concatFrames(OFVector< DcmIODTypes::Frame* > frames,
-                           Uint8* pixData,
-                           const size_t bitsPerFrame);
-
-  /** Add frame to segmentation object.
-   *  @param  pixData Pixel data to be added. Length must be rows*columns bytes.
-   *          Pixel data is copied so it must be freed by the caller.
-   *  @return EC_Normal if adding was successful, error otherwise
-   */
-  virtual OFCondition addFrame(Uint8* pixData);
+    /** Protected default constructor. Library users should the factory create..()
+     *  method in order to create an object from scratch
+     */
+    DcmSegmentation();
+
+    /** Overwrites DcmIODImage::read()
+     *  @param  dataset The dataset to read from
+     *  @return EC_Normal if reading succeeded, error otherwise
+     */
+    OFCondition read(DcmItem& dataset);
+
+    /** Reads dataset without pixel data
+     *  @param  dataset The dataset to read from
+     *  @return EC_Normal if reading succeeded, error otherwise
+     */
+    OFCondition readWithoutPixelData(DcmItem& dataset);
+
+    /** Writes the complete dataset without pixel data
+     *  @param  dataset The dataset to write to
+     *  @param  pixData Buffer for pixel data to write to
+     *  @param  pixDataLength Length of pixData buffer
+     *  @return EC_Normal if writing succeeded, error otherwise
+     */
+    OFCondition writeWithSeparatePixelData(DcmItem& dataset, Uint8*& pixData, size_t& pixDataLength);
+
+    /** Create those data structures common for binary and fractional
+     *  segmentations
+     *  @param  segmentation The segmentation object created
+     *  @param  rows The number of rows for the segmentation
+     *  @param  columns The number of columns for the segmentation
+     *  @param  equipmentInfo Equipment information
+     *  @param  contentIdentification Content meta information
+     *  @return EC_Normal if creation was successful, error otherwise
+     */
+    static OFCondition createCommon(DcmSegmentation*& segmentation,
+                                    const Uint16 rows,
+                                    const Uint16 columns,
+                                    const IODGeneralEquipmentModule::EquipmentInfo& equipmentInfo,
+                                    const ContentIdentificationMacro& contentIdentification);
+
+    /** Hide same function from IODImage since do not want the user to access
+     *  the image pixel module manually.
+     *  @return The Image Pixel Module
+     */
+    virtual IODImagePixelModule<Uint8>& getImagePixel();
+
+    /** Initialize IOD rules
+     */
+    virtual void initIODRules();
+
+    /** Read segments from given item
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition readSegments(DcmItem& item);
+
+    /** Write fractional frames to given pixel data buffer
+     *  @param  pixData The filled pixel data buffer returned by the method
+     *  @param  numFrames The number of frames to write
+     *  @param  pixDataLength The length of buffer in pixData (in bytes) returned by this method.
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition writeFractionalFrames(Uint8* pixData, Uint32 numFrames, const size_t pixDataLength);
+
+    /** Write binary frames to given given pixel data buffer
+     *  @param  pixData The filled pixel data buffer returned by the method
+     *  @param  rows Number of rows in frame
+     *  @param  cols Number of columns in frame
+     *  @param  pixDataLength The length of buffer in pixData (in bytes) returned by this method.
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition writeBinaryFrames(Uint8* pixData, Uint16 rows, Uint16 cols, const size_t pixDataLength);
+
+    /** Write Segmentation Image Module
+     *  @param dataset The item to write to, usually main dataset level
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition writeSegmentationImageModule(DcmItem& dataset);
+
+    /** Write Segments
+     *  @param item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition writeSegments(DcmItem& item);
+
+    /** Write Multi-Frame Functional Groups
+     *  @param dataset The item to write to, usually main dataset level
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition writeMultiFrameFunctionalGroupsModule(DcmItem& dataset);
+
+    /** Write Multi-Frame Dimension Module
+     *  @param dataset The item to write to, usually main dataset level
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition writeMultiFrameDimensionModule(DcmItem& dataset);
+
+    /** Read frames
+     *  @param  dataset Item to read from, usually main dataset level
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition readFrames(DcmItem& dataset);
+
+    /** Get Image Pixel module attributes and perform some basic checking
+     *  @param  dataset Item to read from, usually main dataset level
+     *  @param  allocated Bits Allocated
+     *  @param  stored Bits Stored
+     *  @param  high High Bit
+     *  @param  spp Samples Per Pixel
+     *  @param  pixelRep Pixel Representation
+     *  @param  rows Rows
+     *  @param  cols Columns
+     *  @param  numberOfFrames The number of frames (as set in the dataset)
+     *  @param  colorModel The color model used
+     *  @return EC_Normal if reading/checking was successful, error otherwise
+     */
+    virtual OFCondition getAndCheckImagePixelAttributes(DcmItem& dataset,
+                                                        Uint16& allocated,
+                                                        Uint16& stored,
+                                                        Uint16& high,
+                                                        Uint16& spp,
+                                                        Uint16& pixelRep,
+                                                        Uint16& rows,
+                                                        Uint16& cols,
+                                                        Uint16& numberOfFrames,
+                                                        OFString& colorModel);
+
+    /** This is the counterpart to the extractFrames() function. It takes a number
+     *  of frames that are in binary segmentation format (i.e. "bit-packed") and
+     *  concatenates them together so the resulting memory block fits the Pixel
+     *  Data format for binary segmentations. Thus method ensure that frames
+     *  are aligned bit for bit concatenated to each other with only (if
+     *  applicable) having unused bits after the last frame.
+     *  @param frames The source frames
+     *  @param pixData The pixel data element data to be filled. Size must be
+     *         at least bitsPerFrame * number of frames.
+     *  @param bitsPerFrame Bits required per frame, usually rows * columns
+     */
+    virtual void concatFrames(OFVector<DcmIODTypes::Frame*> frames, Uint8* pixData, const size_t bitsPerFrame);
+
+    /** Add frame to segmentation object.
+     *  @param  pixData Pixel data to be added. Length must be rows*columns bytes.
+     *          Pixel data is copied so it must be freed by the caller.
+     *  @return EC_Normal if adding was successful, error otherwise
+     */
+    virtual OFCondition addFrame(Uint8* pixData);
 
 private:
-
-  // Modules supported:
-  //
-  // Patient Module (through DcmIODImage)
-  // Patient Study Module (through DcmIODImage)
-  // General Study Module (through DcmIODImage)
-  // General Series Module (through DcmIODImage)
-  // Segmentation Series Module
-  // Frame of Reference Module (through DcmIODImage)
-  // General Equipment Module (through DcmIODImage)
-  // Enhanced General Equipment Module (through DcmIODImage)
-  // General Image Module (through DcmIODImage)
-  // Image Pixel Module (through DcmIODImage)
-  // Segmentation Image Module (through this class)
-  // Multi-frame Functional Group Module
-  // Multi-Frame Dimension Module
-  // SOP Common Module (through DcmIODImage)
-  // Common Instance Reference Module (through DcmIODImage)
-
-  /// Segmentation Series Module
-  IODSegmentationSeriesModule m_SegmentationSeries;
-
-  /// IODEnhancedEquipmentModule
-  IODEnhGeneralEquipmentModule m_EnhancedGeneralEquipmentModule;
-
-  /// Multi-frame Functional Groups module
-  IODMultiFrameFGModule m_FG;
-
-  /// Multi-frame Dimension Module
-  IODMultiframeDimensionModule m_DimensionModule;
-
-  /// Binary frame data
-  OFVector<DcmIODTypes::Frame*> m_Frames;
-
-  /* Image level information */
-
-  /// Image Type: (CS, VM 2-n, Type 1), in Segmentations fixed to "DERIVED\PRIMARY"
-  const OFString m_ImageType;
-
-  // Instance Number: (IS, VM 1, Type 1)
-
-  /// Content Identification Macro
-  ContentIdentificationMacro m_ContentIdentificationMacro;
-
-  /// Segmentation Type: (CS, 1, 1)
-  DcmSegTypes::E_SegmentationType m_SegmentationType;
-
-  /// Segmentation Fractional Type: (CS, 1, 1C) (required if FRACTIONAL)
-  DcmSegTypes::E_SegmentationFractionalType m_SegmentationFractionalType;
-
-  /// Maximum Fractional Value: (US, 1, 1C) (required if fractional type is FRACTIONAL)
-  DcmUnsignedShort m_MaximumFractionalValue;
-
-  /// Segment descriptions from Segment Sequence
-  OFVector<DcmSegment*> m_Segments;
-
-  /// Multi-frame Functional Groups high level interface
-  FGInterface m_FGInterface;
-
-  // --------------- private helper functions -------------------
-
-  /** Clear old data
-   */
-  void clearData();
-
-  /** Check the length of the pixel data
-   *  @param  pixelData The Pixel Data element
-   *  @param  rows Number of rows
-   *  @param  cols Number of columns
-   *  @param  numberOfFrames Number of frames
-   *  @result OFTrue if length is valid, OFFalse otherwise
-   */
-  OFBool checkPixDataLength(DcmElement* pixelData,
-                            const Uint16 rows,
-                            const Uint16 cols,
-                            const Uint16& numberOfFrames);
-
-  /** Loads file
-   *  @param  dcmff The file format to load into
-   *  @param  filename The filename of the file to load
-   *  @param  dset Pointer to dataset after loading
-   *  @return EC_Normal if loading was successful, error otherwise
-   */
-  static OFCondition loadFile(DcmFileFormat& dcmff,
-                              const OFString& filename,
-                              DcmDataset*& dset);
-
-  /** Computes the number of total bytes required for the frame data of this
-   *  segmentation object. Takes into account dimensions and number of frames,
-   *  as well as the type of segmentation (member variables). May file if
-   *  size_t type is not able to hold the result of intermediate computations.
-   *  @param  rows Number of rows of a frame
-   *  @param  cols Number of cols of a frame
-   *  @param  numberOfFrames The number of frames of the object
-   *  @param  bytesRequired Will hold the result of the computation,
-   *          if successful. Does not any padding into account.
-   *  @return EC_Normal if computation was possible, EC_TooManyBytesRequested
-   *          otherwise.
-   */
-  OFCondition getTotalBytesRequired(const Uint16& rows,
-                                    const Uint16& cols,
-                                    const Uint32& numberOfFrames,
-                                    size_t& bytesRequired);
-
-  /** Read Fractional Type of segmentation.
-   *  @param  item The item to read from
-   *  @return EC_Normal if type could be read, EC_TagNotFound if tag is not present,
-   *  error otherwise
-   */
-  OFCondition readSegmentationFractionalType(DcmItem& item);
-
-  /** Read Segmentation Type of segmentation object
-   *  @param  item The item to read from
-   *  @return EC_Normal if type could be read, EC_TagNotFound if tag is not present,
-   *  error otherwise
-   */
-  OFCondition readSegmentationType(DcmItem& item);
-
-  /** Decompress the given dataset
-   *  @param  dset The dataset to be decompressed
-   *  @return EC_Normal if decompression worked (or dataset has already been
-   *  decompressed), IOD_EC_CannotDecompress otherwise
-   */
-  static OFCondition decompress(DcmDataset& dset);
-
+    // Modules supported:
+    //
+    // Patient Module (through DcmIODImage)
+    // Patient Study Module (through DcmIODImage)
+    // General Study Module (through DcmIODImage)
+    // General Series Module (through DcmIODImage)
+    // Segmentation Series Module
+    // Frame of Reference Module (through DcmIODImage)
+    // General Equipment Module (through DcmIODImage)
+    // Enhanced General Equipment Module (through DcmIODImage)
+    // General Image Module (through DcmIODImage)
+    // Image Pixel Module (through DcmIODImage)
+    // Segmentation Image Module (through this class)
+    // Multi-frame Functional Group Module
+    // Multi-Frame Dimension Module
+    // SOP Common Module (through DcmIODImage)
+    // Common Instance Reference Module (through DcmIODImage)
+
+    /// Segmentation Series Module
+    IODSegmentationSeriesModule m_SegmentationSeries;
+
+    /// IODEnhancedEquipmentModule
+    IODEnhGeneralEquipmentModule m_EnhancedGeneralEquipmentModule;
+
+    /// Multi-frame Functional Groups module
+    IODMultiFrameFGModule m_FG;
+
+    /// Multi-frame Dimension Module
+    IODMultiframeDimensionModule m_DimensionModule;
+
+    /// Binary frame data
+    OFVector<DcmIODTypes::Frame*> m_Frames;
+
+    /* Image level information */
+
+    /// Image Type: (CS, VM 2-n, Type 1), in Segmentations fixed to "DERIVED\PRIMARY"
+    const OFString m_ImageType;
+
+    // Instance Number: (IS, VM 1, Type 1)
+
+    /// Content Identification Macro
+    ContentIdentificationMacro m_ContentIdentificationMacro;
+
+    /// Segmentation Type: (CS, 1, 1)
+    DcmSegTypes::E_SegmentationType m_SegmentationType;
+
+    /// Segmentation Fractional Type: (CS, 1, 1C) (required if FRACTIONAL)
+    DcmSegTypes::E_SegmentationFractionalType m_SegmentationFractionalType;
+
+    /// Maximum Fractional Value: (US, 1, 1C) (required if fractional type is FRACTIONAL)
+    DcmUnsignedShort m_MaximumFractionalValue;
+
+    /// Segment descriptions from Segment Sequence
+    OFVector<DcmSegment*> m_Segments;
+
+    /// Multi-frame Functional Groups high level interface
+    FGInterface m_FGInterface;
+
+    // --------------- private helper functions -------------------
+
+    /** Clear old data
+     */
+    void clearData();
+
+    /** Check the length of the pixel data
+     *  @param  pixelData The Pixel Data element
+     *  @param  rows Number of rows
+     *  @param  cols Number of columns
+     *  @param  numberOfFrames Number of frames
+     *  @result OFTrue if length is valid, OFFalse otherwise
+     */
+    OFBool
+    checkPixDataLength(DcmElement* pixelData, const Uint16 rows, const Uint16 cols, const Uint16& numberOfFrames);
+
+    /** Loads file
+     *  @param  dcmff The file format to load into
+     *  @param  filename The filename of the file to load
+     *  @param  dset Pointer to dataset after loading
+     *  @return EC_Normal if loading was successful, error otherwise
+     */
+    static OFCondition loadFile(DcmFileFormat& dcmff, const OFString& filename, DcmDataset*& dset);
+
+    /** Computes the number of total bytes required for the frame data of this
+     *  segmentation object. Takes into account dimensions and number of frames,
+     *  as well as the type of segmentation (member variables). May file if
+     *  size_t type is not able to hold the result of intermediate computations.
+     *  @param  rows Number of rows of a frame
+     *  @param  cols Number of cols of a frame
+     *  @param  numberOfFrames The number of frames of the object
+     *  @param  bytesRequired Will hold the result of the computation,
+     *          if successful. Does not any padding into account.
+     *  @return EC_Normal if computation was possible, EC_TooManyBytesRequested
+     *          otherwise.
+     */
+    OFCondition
+    getTotalBytesRequired(const Uint16& rows, const Uint16& cols, const Uint32& numberOfFrames, size_t& bytesRequired);
+
+    /** Read Fractional Type of segmentation.
+     *  @param  item The item to read from
+     *  @return EC_Normal if type could be read, EC_TagNotFound if tag is not present,
+     *  error otherwise
+     */
+    OFCondition readSegmentationFractionalType(DcmItem& item);
+
+    /** Read Segmentation Type of segmentation object
+     *  @param  item The item to read from
+     *  @return EC_Normal if type could be read, EC_TagNotFound if tag is not present,
+     *  error otherwise
+     */
+    OFCondition readSegmentationType(DcmItem& item);
+
+    /** Decompress the given dataset
+     *  @param  dset The dataset to be decompressed
+     *  @return EC_Normal if decompression worked (or dataset has already been
+     *  decompressed), IOD_EC_CannotDecompress otherwise
+     */
+    static OFCondition decompress(DcmDataset& dset);
 };
 
 #endif // SEGDOC_H
index f2f0d444131963568acea662e781b8579d9df272..f7987c0c9de0446ed4ad849886d75488ceb782b5 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #ifndef SEGMENT_H
 #define SEGMENT_H
 
-#include "dcmtk/config/osconfig.h"  // include OS configuration first
+#include "dcmtk/config/osconfig.h" // include OS configuration first
+
 #include "dcmtk/dcmdata/dcvrus.h"
 #include "dcmtk/dcmiod/iodmacro.h"
-#include "dcmtk/dcmseg/segtypes.h"
 #include "dcmtk/dcmseg/segdoc.h"
+#include "dcmtk/dcmseg/segtypes.h"
 
 /** Class representing a segment from the Segment Identification Sequence,
  *  as used within the Segmentation Image Module. It includes the Segment
@@ -37,302 +38,282 @@ class DCMTK_DCMSEG_EXPORT DcmSegment
 {
 
 public:
-
-  // -------------- constructors/destructors --------------------
-
-  // constructor is protected
-
-  /** Destructor, frees memory
-   */
-  virtual ~DcmSegment();
-
-  /** Clears all data
-   */
-  virtual void clearData();
-
-  // -------------- creation --------------------
-
-  /** Factory method to create a Segment that expects the minimal parameters
-   *  required.
-   *  @param  segment Pointer to the resulting segment if creation was
-   *          successful; memory is allocated by the function
-   *  @param  segmentLabel Free text label for the segment
-   *  @param  segmentedPropertyCategory The segmented property category.
-   *          Baseline CID 7150 “Segmentation Property Categories” should be
-   *          used.
-   *  @param  segmentedPropertyType The segmented property type. Baseline CID
-   *          7151 “Segmentation Property Types”
-   *  @param  algoType The algorithm type used for segmenting this segment
-   *  @param  algoName Algorithm name (required if algoType is not MANUAL)
-   *  @return EC_Normal if creation was successful, error otherwise
-   */
-  static OFCondition create(DcmSegment*& segment,
-                            const OFString& segmentLabel,
-                            const CodeSequenceMacro& segmentedPropertyCategory,
-                            const CodeSequenceMacro& segmentedPropertyType,
-                            const DcmSegTypes::E_SegmentAlgoType algoType,
-                            const OFString& algoName = "");
-
-  // ---------------- writing --------------------
-
-  /** Write segment to given item which is usually contained within
-   *  within the Segment Sequence
-   *  @param  item The item to write to
-   *  @return EC_Normal if successful, error otherwise
-   */
-  OFCondition write(DcmItem& item);
-
-  // ---------------- reading --------------------
-
-  /** Read segment from given item
-   *  @param  item The item to read from (must be item as found in the
-   *          Segment Identification Sequence)
-   *  @param  clearOldData If true, old data is deleted first
-   *  @return  EC_Normal if reading was successful, error otherwise
-   */
-  OFCondition read(DcmItem& item,
-                   const OFBool clearOldData = OFTrue);
-
-  // ---------------- access --------------------
-
-  /** Get Segment Number
-   *  @return The Segment number
-   */
-  virtual unsigned int getSegmentNumber();
-
-  /** Get Segment Label
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getSegmentLabel(OFString& value,
-                                      const signed long pos = 0);
-
-  /** Get Segment Description
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getSegmentDescription(OFString& value,
-                                            const signed long pos = 0);
-
-  /** Get the Segment Algorithm Type.
-   *  @return The Algorithm Type
-   */
-  virtual DcmSegTypes::E_SegmentAlgoType getSegmentAlgorithmType();
-
-  /** Get the Segment Algorithm Name
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getSegmentAlgorithmName(OFString& value,
-                                              const signed long pos = 0);
-
-  /** Get General Anatomy Code
-   *  @return Reference to the General Anatomy Macro, may be unset
-   */
-  virtual GeneralAnatomyMacro& getGeneralAnatomyCode();
-
-  /** Get Segmented Property Category Code
-   *  @return Reference to the Segmented Property Category Code, may be unset
-   */
-  virtual CodeSequenceMacro& getSegmentedPropertyCategoryCode();
-
-  /** Get Segmented Property Type  Code
-   *  @return Reference to the Segmented Property Type Code, may be unset
-   */
-  virtual CodeSequenceMacro& getSegmentedPropertyTypeCode();
-
-  /** Get Segmented Property Type Modifier Code
-   *  @return Reference to the Segmented Property Type Modifier Code, may
-   *  be unset
-   */
-  virtual OFVector<CodeSequenceMacro*>& getSegmentedPropertyTypeModifierCode();
-
-  /** Get Segmentation Algorithm Identification
-   *  @warning This method has earlier been named getSegmentSurfaceGenerationAlgorithmIdentification()
-   *           which has changed due to DICOM CP-1597. The code value returned is now
-   *           taken from the "Segmentation Algorithm Identification Sequence" instead of the
-   *           "Segment Surface Generation Algorithm Identification Sequence".
-   *  @return Reference to the Segmentation Algorithm Identification
-   *  Identification, may be unset
-   */
-  virtual AlgorithmIdentificationMacro& getSegmentationAlgorithmIdentification();
-
-  /** Get Recommended Display Grayscale Value
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1)
-   *  @return EC_Normal if successful, an error code otherwise
-   */  virtual OFCondition getRecommendedDisplayGrayscaleValue(Uint16& value,
-                                                               const unsigned long pos = 0);
-
-  /** Returns Recommended Display CIELab Value
-   *  @param  L The L component
-   *  @param  a The a* component
-   *  @param  b The b* component
-   *  @return EC_Normal if values could be returned
-   */
-  virtual OFCondition getRecommendedDisplayCIELabValue(Uint16& L,
-                                                       Uint16& a,
-                                                       Uint16& b);
-
-  /** Get Tracking ID
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getTrackingID(OFString& value,
-                                    const signed long pos = 0);
-
-  /** Get Tracking UID
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getTrackingUID(OFString& value,
-                                     const signed long pos = 0);
-
-
-  // -------------- setters --------------------
-
-  /** Set Segment Label
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSegmentLabel(const OFString& value,
-                                      const OFBool checkValue = OFTrue);
-
-  /** Set Segment Label
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (ST) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSegmentDescription(const OFString& value,
+    // -------------- constructors/destructors --------------------
+
+    // constructor is protected
+
+    /** Destructor, frees memory
+     */
+    virtual ~DcmSegment();
+
+    /** Clears all data
+     */
+    virtual void clearData();
+
+    // -------------- creation --------------------
+
+    /** Factory method to create a Segment that expects the minimal parameters
+     *  required.
+     *  @param  segment Pointer to the resulting segment if creation was
+     *          successful; memory is allocated by the function
+     *  @param  segmentLabel Free text label for the segment
+     *  @param  segmentedPropertyCategory The segmented property category.
+     *          Baseline CID 7150 “Segmentation Property Categories” should be
+     *          used.
+     *  @param  segmentedPropertyType The segmented property type. Baseline CID
+     *          7151 “Segmentation Property Types”
+     *  @param  algoType The algorithm type used for segmenting this segment
+     *  @param  algoName Algorithm name (required if algoType is not MANUAL)
+     *  @return EC_Normal if creation was successful, error otherwise
+     */
+    static OFCondition create(DcmSegment*& segment,
+                              const OFString& segmentLabel,
+                              const CodeSequenceMacro& segmentedPropertyCategory,
+                              const CodeSequenceMacro& segmentedPropertyType,
+                              const DcmSegTypes::E_SegmentAlgoType algoType,
+                              const OFString& algoName = "");
+
+    // ---------------- writing --------------------
+
+    /** Write segment to given item which is usually contained within
+     *  within the Segment Sequence
+     *  @param  item The item to write to
+     *  @return EC_Normal if successful, error otherwise
+     */
+    OFCondition write(DcmItem& item);
+
+    // ---------------- reading --------------------
+
+    /** Read segment from given item
+     *  @param  item The item to read from (must be item as found in the
+     *          Segment Identification Sequence)
+     *  @param  clearOldData If true, old data is deleted first
+     *  @return  EC_Normal if reading was successful, error otherwise
+     */
+    OFCondition read(DcmItem& item, const OFBool clearOldData = OFTrue);
+
+    // ---------------- access --------------------
+
+    /** Get Segment Number
+     *  @return The Segment number
+     */
+    virtual unsigned int getSegmentNumber();
+
+    /** Get Segment Label
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSegmentLabel(OFString& value, const signed long pos = 0);
+
+    /** Get Segment Description
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSegmentDescription(OFString& value, const signed long pos = 0);
+
+    /** Get the Segment Algorithm Type.
+     *  @return The Algorithm Type
+     */
+    virtual DcmSegTypes::E_SegmentAlgoType getSegmentAlgorithmType();
+
+    /** Get the Segment Algorithm Name
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSegmentAlgorithmName(OFString& value, const signed long pos = 0);
+
+    /** Get General Anatomy Code
+     *  @return Reference to the General Anatomy Macro, may be unset
+     */
+    virtual GeneralAnatomyMacro& getGeneralAnatomyCode();
+
+    /** Get Segmented Property Category Code
+     *  @return Reference to the Segmented Property Category Code, may be unset
+     */
+    virtual CodeSequenceMacro& getSegmentedPropertyCategoryCode();
+
+    /** Get Segmented Property Type  Code
+     *  @return Reference to the Segmented Property Type Code, may be unset
+     */
+    virtual CodeSequenceMacro& getSegmentedPropertyTypeCode();
+
+    /** Get Segmented Property Type Modifier Code
+     *  @return Reference to the Segmented Property Type Modifier Code, may
+     *  be unset
+     */
+    virtual OFVector<CodeSequenceMacro*>& getSegmentedPropertyTypeModifierCode();
+
+    /** Get Segmentation Algorithm Identification
+     *  @warning This method has earlier been named getSegmentSurfaceGenerationAlgorithmIdentification()
+     *           which has changed due to DICOM CP-1597. The code value returned is now
+     *           taken from the "Segmentation Algorithm Identification Sequence" instead of the
+     *           "Segment Surface Generation Algorithm Identification Sequence".
+     *  @return Reference to the Segmentation Algorithm Identification
+     *  Identification, may be unset
+     */
+    virtual AlgorithmIdentificationMacro& getSegmentationAlgorithmIdentification();
+
+    /** Get Recommended Display Grayscale Value
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1)
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getRecommendedDisplayGrayscaleValue(Uint16& value, const unsigned long pos = 0);
+
+    /** Returns Recommended Display CIELab Value
+     *  @param  L The L component
+     *  @param  a The a* component
+     *  @param  b The b* component
+     *  @return EC_Normal if values could be returned
+     */
+    virtual OFCondition getRecommendedDisplayCIELabValue(Uint16& L, Uint16& a, Uint16& b);
+
+    /** Get Tracking ID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getTrackingID(OFString& value, const signed long pos = 0);
+
+    /** Get Tracking UID
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getTrackingUID(OFString& value, const signed long pos = 0);
+
+    // -------------- setters --------------------
+
+    /** Set Segment Label
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSegmentLabel(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Segment Label
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (ST) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSegmentDescription(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Segment Algorithm
+     *  @param  algoType Algorithm type used to find segment
+     *  @param  algoName Name of the algorithm used (required if algorithm type
+     *          is not MANUAL
+     *  @param  checkValue If OFTrue, input is checked for validity
+     *  @return EC_Normal if setting was successful, error otherwise
+     */
+    virtual OFCondition setSegmentAlgorithm(const DcmSegTypes::E_SegmentAlgoType algoType,
+                                            const OFString& algoName,
                                             const OFBool checkValue = OFTrue);
 
-  /** Set Segment Algorithm
-   *  @param  algoType Algorithm type used to find segment
-   *  @param  algoName Name of the algorithm used (required if algorithm type
-   *          is not MANUAL
-   *  @param  checkValue If OFTrue, input is checked for validity
-   *  @return EC_Normal if setting was successful, error otherwise
-   */
-  virtual OFCondition setSegmentAlgorithm(const DcmSegTypes::E_SegmentAlgoType algoType,
-                                          const OFString& algoName,
-                                          const OFBool checkValue = OFTrue);
-
-  /** Set Segmentation Algorithm Identification
-   *  @warning This method has earlier been named setSegmentSurfaceGenerationAlgorithmIdentification()
-   *           which has changed due to DICOM CP-1597. The resulting code value is now
-   *           written to the "Segmentation Algorithm Identification Sequence" instead of the
-   *           "Segment Surface Generation Algorithm Identification Sequence".
-   *  @param  value The algorithm identification
-   *  @param  checkValue If OFTrue, value undergoes some validity checks
-   *  @return EC_Normal if setting was successful, error otherwise
-   */
-  virtual OFCondition setSegmentationAlgorithmIdentification(const AlgorithmIdentificationMacro& value,
-                                                             const OFBool checkValue = OFTrue);
-
-  /** Set Recommended Display Grayscale Value
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for validity if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRecommendedDisplayGrayscaleValue(const Uint16 value,
-                                                          const OFBool checkValue = OFTrue);
-
-  /** Set Recommended Display CIELab Value
-   *  @param  L L component
-   *  @param  a a component
-   *  @param  b b component
-   *  @param  checkValue Check 'value' for validity if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setRecommendedDisplayCIELabValue(const Uint16 L,
-                                                       const Uint16 a,
-                                                       const Uint16 b,
-                                                       const OFBool checkValue = OFTrue);
-
-  /** Set Tracking ID
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setTrackingID(const OFString& value,
-                                    const OFBool checkValue = OFTrue);
-
-  /** Set Tracking UID
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (UI) and VM (1) if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setTrackingUID(const OFString& value,
-                                     const OFBool checkValue = OFTrue);
-
-  /// The utility class must access the protected default constructor
-  friend class DcmIODUtil;
+    /** Set Segmentation Algorithm Identification
+     *  @warning This method has earlier been named setSegmentSurfaceGenerationAlgorithmIdentification()
+     *           which has changed due to DICOM CP-1597. The resulting code value is now
+     *           written to the "Segmentation Algorithm Identification Sequence" instead of the
+     *           "Segment Surface Generation Algorithm Identification Sequence".
+     *  @param  value The algorithm identification
+     *  @param  checkValue If OFTrue, value undergoes some validity checks
+     *  @return EC_Normal if setting was successful, error otherwise
+     */
+    virtual OFCondition setSegmentationAlgorithmIdentification(const AlgorithmIdentificationMacro& value,
+                                                               const OFBool checkValue = OFTrue);
+
+    /** Set Recommended Display Grayscale Value
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for validity if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setRecommendedDisplayGrayscaleValue(const Uint16 value, const OFBool checkValue = OFTrue);
+
+    /** Set Recommended Display CIELab Value
+     *  @param  L L component
+     *  @param  a a component
+     *  @param  b b component
+     *  @param  checkValue Check 'value' for validity if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition
+    setRecommendedDisplayCIELabValue(const Uint16 L, const Uint16 a, const Uint16 b, const OFBool checkValue = OFTrue);
+
+    /** Set Tracking ID
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setTrackingID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /** Set Tracking UID
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (UI) and VM (1) if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setTrackingUID(const OFString& value, const OFBool checkValue = OFTrue);
+
+    /// The utility class must access the protected default constructor
+    friend class DcmIODUtil;
 
 protected:
+    /** Protected default constructor
+     */
+    DcmSegment();
 
-  /** Protected default constructor
-   */
-  DcmSegment();
-
-  /** Initialize IOD rules for this component
-   */
-  virtual void initIODRules();
-
-  /** Set reference to the Segmentation object that this segment belongs to.
-   *  This is used to find the Segment Number this Segment has within the
-   *  Segmentation.
-   *  @param  doc Pointer to the Segmentation object
-   */
-  void referenceSegmentationDoc(DcmSegmentation* doc);
+    /** Initialize IOD rules for this component
+     */
+    virtual void initIODRules();
 
+    /** Set reference to the Segmentation object that this segment belongs to.
+     *  This is used to find the Segment Number this Segment has within the
+     *  Segmentation.
+     *  @param  doc Pointer to the Segmentation object
+     */
+    void referenceSegmentationDoc(DcmSegmentation* doc);
 
 private:
+    /** Private undefined copy constructor
+     */
+    DcmSegment(const DcmSegment&);
 
-  /** Private undefined copy constructor
-   */
-  DcmSegment(const DcmSegment&);
-
-  /** Private undefined assignment operator
-   *  @return Reference to "this" class
-   */
-  DcmSegment& operator=(const DcmSegment&);
+    /** Private undefined assignment operator
+     *  @return Reference to "this" class
+     */
+    DcmSegment& operator=(const DcmSegment&);
 
-  /// The segmentation document where this segment is located in
-  DcmSegmentation* m_SegmentationDoc;
+    /// The segmentation document where this segment is located in
+    DcmSegmentation* m_SegmentationDoc;
 
-  /// Segment Description Macro
-  SegmentDescriptionMacro m_SegmentDescription;
+    /// Segment Description Macro
+    SegmentDescriptionMacro m_SegmentDescription;
 
-  /// Segment Algorithm Name: (LO, 1, 1C)
-  DcmLongString m_SegmentAlgorithmName;
+    /// Segment Algorithm Name: (LO, 1, 1C)
+    DcmLongString m_SegmentAlgorithmName;
 
-  /// Segmentation Algorithm Identification (SQ, 1, 3).
-  /// This attribute has earlier been named m_SegmentationSurfaceGenerationAlgorithmIdentification
-  /// representing the related sequence. This has been changed in favor of the
-  /// Segmentation Algorithm Identification Sequence due to DICOM CP-1597.
-  AlgorithmIdentificationMacro m_SegmentationAlgorithmIdentification;
+    /// Segmentation Algorithm Identification (SQ, 1, 3).
+    /// This attribute has earlier been named m_SegmentationSurfaceGenerationAlgorithmIdentification
+    /// representing the related sequence. This has been changed in favor of the
+    /// Segmentation Algorithm Identification Sequence due to DICOM CP-1597.
+    AlgorithmIdentificationMacro m_SegmentationAlgorithmIdentification;
 
-  /// Recommended Display Grayscale Value (US, 1, 3)
-  DcmUnsignedShort m_RecommendedDisplayGrayscaleValue;
+    /// Recommended Display Grayscale Value (US, 1, 3)
+    DcmUnsignedShort m_RecommendedDisplayGrayscaleValue;
 
-  /// Recommended Display CIELab Value (US, 3, 3)
-  DcmUnsignedShort m_RecommendedDisplayCIELabValue;
+    /// Recommended Display CIELab Value (US, 3, 3)
+    DcmUnsignedShort m_RecommendedDisplayCIELabValue;
 
-  /// Tracking ID (UT, 1, 1C)
-  DcmUnlimitedText m_TrackingID;
+    /// Tracking ID (UT, 1, 1C)
+    DcmUnlimitedText m_TrackingID;
 
-  /// Tracking UID (UI, 1, 1C)
-  DcmUniqueIdentifier m_TrackingUID;
+    /// Tracking UID (UI, 1, 1C)
+    DcmUniqueIdentifier m_TrackingUID;
 
-  /// Rules for data elements within this IOD
-  IODRules m_Rules;
+    /// Rules for data elements within this IOD
+    IODRules m_Rules;
 };
 
 #endif // SEGMENT_H
index 283beb4d8659c1f0929baefc1607cd4865faa00e..450831e87d4b447cd2efa6d6f2f1dca52a9c8e2b 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2020, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
 #define SEGTYPES_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/oflog/oflog.h"
+
 #include "dcmtk/dcmiod/iodmacro.h"
 #include "dcmtk/dcmseg/segdef.h"
+#include "dcmtk/oflog/oflog.h"
 
 /*
  * *  Logging
  */
 
-extern OFString c;
 extern DCMTK_DCMSEG_EXPORT OFLogger DCM_dcmsegLogger;
 
 #define DCMSEG_TRACE(msg) OFLOG_TRACE(DCM_dcmsegLogger, msg)
 #define DCMSEG_DEBUG(msg) OFLOG_DEBUG(DCM_dcmsegLogger, msg)
-#define DCMSEG_INFO(msg)  OFLOG_INFO(DCM_dcmsegLogger, msg)
-#define DCMSEG_WARN(msg)  OFLOG_WARN(DCM_dcmsegLogger, msg)
+#define DCMSEG_INFO(msg) OFLOG_INFO(DCM_dcmsegLogger, msg)
+#define DCMSEG_WARN(msg) OFLOG_WARN(DCM_dcmsegLogger, msg)
 #define DCMSEG_ERROR(msg) OFLOG_ERROR(DCM_dcmsegLogger, msg)
 #define DCMSEG_FATAL(msg) OFLOG_FATAL(DCM_dcmsegLogger, msg)
 
@@ -64,15 +64,15 @@ const Uint32 DCM_SEG_MAX_SEGMENTS = 65535;
 //@{
 
 /// error: specified functional group is already existing
-extern DCMTK_DCMSEG_EXPORT   const OFConditionConst     SG_EC_MaxSegmentsReached;
+extern DCMTK_DCMSEG_EXPORT const OFConditionConst SG_EC_MaxSegmentsReached;
 /// error: specified segment does not exist
-extern DCMTK_DCMSEG_EXPORT   const OFConditionConst     SG_EC_NoSuchSegment;
+extern DCMTK_DCMSEG_EXPORT const OFConditionConst SG_EC_NoSuchSegment;
 /// error: unknown segmentation type
-extern DCMTK_DCMSEG_EXPORT   const OFConditionConst     SG_EC_UnknownSegmentationType;
+extern DCMTK_DCMSEG_EXPORT const OFConditionConst SG_EC_UnknownSegmentationType;
 /// error: invalid value
-extern DCMTK_DCMSEG_EXPORT   const OFConditionConst     SG_EC_InvalidValue;
+extern DCMTK_DCMSEG_EXPORT const OFConditionConst SG_EC_InvalidValue;
 /// error: not enough data
-extern DCMTK_DCMSEG_EXPORT   const OFConditionConst     SG_EC_NotEnoughData;
+extern DCMTK_DCMSEG_EXPORT const OFConditionConst SG_EC_NotEnoughData;
 
 /** General purpose class hiding global functions, constants and types in the
  *  segmentation context from the global namespace.
@@ -80,57 +80,54 @@ extern DCMTK_DCMSEG_EXPORT   const OFConditionConst     SG_EC_NotEnoughData;
 class DCMTK_DCMSEG_EXPORT DcmSegTypes
 {
 
-  public:
-
-   /** Segmentation object types
+public:
+    /** Segmentation object types
      */
     enum E_SegmentationType
     {
-      /// Unknown (e.g.\ not initialized)
-      ST_UNKNOWN,
-      /// Binary segmentation with 1 bit depth denoting whether a pixel
-      /// belongs to a segmentation or not.
-      ST_BINARY,
-      /// Fractional segmentation where fraction specifies how much of voxel
-      /// is occupied by the segment
-      ST_FRACTIONAL
+        /// Unknown (e.g.\ not initialized)
+        ST_UNKNOWN,
+        /// Binary segmentation with 1 bit depth denoting whether a pixel
+        /// belongs to a segmentation or not.
+        ST_BINARY,
+        /// Fractional segmentation where fraction specifies how much of voxel
+        /// is occupied by the segment
+        ST_FRACTIONAL
     };
 
     /** Segment Algorithm Type
      */
     enum E_SegmentAlgoType
     {
-      /// Unknown (e.g.\ not initialized)
-      SAT_UNKNOWN,
-      /// Calculated segment
-      SAT_AUTOMATIC,
-      /// Calculated segment with user interaction
-      SAT_SEMIAUTOMATIC,
-      /// Manual segment creation
-      SAT_MANUAL
+        /// Unknown (e.g.\ not initialized)
+        SAT_UNKNOWN,
+        /// Calculated segment
+        SAT_AUTOMATIC,
+        /// Calculated segment with user interaction
+        SAT_SEMIAUTOMATIC,
+        /// Manual segment creation
+        SAT_MANUAL
     };
 
-
     /** Segmentation object Fractional Type
      */
     enum E_SegmentationFractionalType
     {
-      /// Unknown (e.g.\ not initialized)
-      SFT_UNKNOWN,
-      /// For fractional segmentations, a value defines probability that pixel belongs to segment
-      SFT_PROBABILITY,
-      /// For fractional segmentations, a value defines how much of the pixel is covered by the segment
-      SFT_OCCUPANCY
+        /// Unknown (e.g.\ not initialized)
+        SFT_UNKNOWN,
+        /// For fractional segmentations, a value defines probability that pixel belongs to segment
+        SFT_PROBABILITY,
+        /// For fractional segmentations, a value defines how much of the pixel is covered by the segment
+        SFT_OCCUPANCY
     };
 
-
     // -- helper functions --
 
     /** Return string representation of algorithm type
      *  @param  algo The algorithm type
      *  @return The algorithm type as a string
      */
-    static OFString algoType2OFString(E_SegmentAlgoType algo );
+    static OFString algoType2OFString(E_SegmentAlgoType algo);
 
     /** Return enum representation of algorithm type string as found in
      *  segmentation objects
@@ -144,20 +141,20 @@ class DCMTK_DCMSEG_EXPORT DcmSegTypes
      *  @param  value The segmentation type as a string
      *  @return The segmentation type as enum value
      */
-    static DcmSegTypes::E_SegmentationType OFString2Segtype( const OFString& value );
+    static DcmSegTypes::E_SegmentationType OFString2Segtype(const OFString& value);
 
     /** Return string representation from segmentation enum type
      *  @param  value The segmentation type as enum value
      *  @return The segmentation type as a string
      */
-    static OFString segtype2OFString( const DcmSegTypes::E_SegmentationType& value );
+    static OFString segtype2OFString(const DcmSegTypes::E_SegmentationType& value);
 
     /** Return enum representation of fractional type string as found in
      *  segmentation objects
      *  @param  value The fractional type as a string
      *  @return The fractional type as enum value
      */
-    static DcmSegTypes::E_SegmentationFractionalType OFString2FractionalType( const OFString& value );
+    static DcmSegTypes::E_SegmentationFractionalType OFString2FractionalType(const OFString& value);
 };
 
 /** Class representing the Segmented Property Type Code and Segmented
@@ -167,60 +164,56 @@ class DCMTK_DCMSEG_EXPORT SegmentedPropertyTypeCodeItem
 {
 
 public:
+    /// Easy access to containing class
+    friend class SegmentDescriptionMacro;
 
-  /// Easy access to containing class
-  friend class SegmentDescriptionMacro;
-
-  /** Constructor
-   */
-  SegmentedPropertyTypeCodeItem();
-
-  /** Virtual destructor, frees memory
-   */
-  virtual ~SegmentedPropertyTypeCodeItem();
-
-  /** Clear all data
-   */
-  virtual void clearData();
-
-  /** Check whether class has valid data
-   *  @param  quiet If OFTrue, check will not produce any warnings or errors
-   *          on the logger. Default is OFFalse.
-   *  @return EC_Normal if data is valid, error otherwise
-   */
-  virtual OFCondition check(const OFBool quiet = OFFalse);
-
-  /** Read data from given item
-   *  @param  item The item to read from
-   *  @param  clearOldData If OFTrue, old data is cleared before reading
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& item,
-                           const OFBool clearOldData = OFTrue);
-
-  /** Write data to given item
-   *  @param item  The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
+    /** Constructor
+     */
+    SegmentedPropertyTypeCodeItem();
 
-protected:
+    /** Virtual destructor, frees memory
+     */
+    virtual ~SegmentedPropertyTypeCodeItem();
 
-  /** Check whether the modifier codes are ok
-   *  @param  quiet If OFTrue, no warnings or errors will be printed to the
-   *          loggers. Default is OFFalse.
-   *  @return EC_Normal if data is ok, error otherwise
-   */
-  OFCondition checkModifiers(const OFBool quiet = OFFalse);
+    /** Clear all data
+     */
+    virtual void clearData();
 
-private:
+    /** Check whether class has valid data
+     *  @param  quiet If OFTrue, check will not produce any warnings or errors
+     *          on the logger. Default is OFFalse.
+     *  @return EC_Normal if data is valid, error otherwise
+     */
+    virtual OFCondition check(const OFBool quiet = OFFalse);
 
-  /// Segmented Property Type Code (SQ,1,1)
-  /// Baseline CID 7151
-  CodeSequenceMacro m_SegmentedPropertyTypeCode;
+    /** Read data from given item
+     *  @param  item The item to read from
+     *  @param  clearOldData If OFTrue, old data is cleared before reading
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item, const OFBool clearOldData = OFTrue);
+
+    /** Write data to given item
+     *  @param item  The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
 
-   /// Segmented Property Type Modifier Code (SQ, VM 1-n, Type 3)
-  OFVector<CodeSequenceMacro*> m_SegmentedPropertyTypeModifierCode;
+protected:
+    /** Check whether the modifier codes are ok
+     *  @param  quiet If OFTrue, no warnings or errors will be printed to the
+     *          loggers. Default is OFFalse.
+     *  @return EC_Normal if data is ok, error otherwise
+     */
+    OFCondition checkModifiers(const OFBool quiet = OFFalse);
+
+private:
+    /// Segmented Property Type Code (SQ,1,1)
+    /// Baseline CID 7151
+    CodeSequenceMacro m_SegmentedPropertyTypeCode;
+
+    /// Segmented Property Type Modifier Code (SQ, VM 1-n, Type 3)
+    OFVector<CodeSequenceMacro*> m_SegmentedPropertyTypeModifierCode;
 };
 
 /** Class representing the Segment Description Macro
@@ -229,135 +222,125 @@ class DCMTK_DCMSEG_EXPORT SegmentDescriptionMacro
 {
 
 public:
+    /** Constructor
+     */
+    SegmentDescriptionMacro();
+
+    /** Virtual destructor, frees memory
+     */
+    virtual ~SegmentDescriptionMacro();
 
-  /** Constructor
-   */
-  SegmentDescriptionMacro();
-
-  /** Virtual destructor, frees memory
-   */
-  virtual ~SegmentDescriptionMacro();
-
-  /** Clear all data
-   */
-  virtual void clearData();
-
-  /** Read class data from given item
-   *  @param  item The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition read(DcmItem& item);
-
-  /** Writes the data from this class to given item
-   *  @param  item The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition write(DcmItem& item);
-
-  /** Get Segment Label
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getSegmentLabel(OFString& value,
-                                      const signed long pos = 0);
-
-  /** Get Segment Description
-   *  @param  value Reference to variable in which the value should be stored
-   *  @param  pos Index of the value to get (0..vm-1), -1 for all components
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition getSegmentDescription(OFString& value,
-                                            const signed long pos = 0);
-
-  /** Get Segment Algorithm Type
-   *  @return The algorithm type
-   */
-  virtual DcmSegTypes::E_SegmentAlgoType getSegmentAlgorithmType();
-
-  /** Get reference to General Anatomy Code
-   *  @return Reference to General Anatomy Code
-   */
-  virtual GeneralAnatomyMacro& getGeneralAnatomyCode();
-
-  /** Get Reference to Segmented Property Category Code
-   *  @return Reference to Segmented Property Category Code
-   */
-  virtual CodeSequenceMacro& getSegmentedPropertyCategoryCode();
-
-  /** Get Reference to Segmented Property Type Code
-   *  @return Reference to Segmented Property Type Code
-   */
-  virtual CodeSequenceMacro& getSegmentedPropertyTypeCode();
-
-  /** Get Reference to Segmented Property Type Modifier Codes
-   *  @return Reference to Segmented Property Type Modifier Codes
-   */
-  virtual OFVector<CodeSequenceMacro*>& getSegmentedPropertyTypeModifier();
-
-  /** Set Segment Label
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1)
-   *          if enabled
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSegmentLabel(const OFString& value,
-                                      const OFBool checkValue = OFTrue);
-
-  /** Set Segment Description
-   *  @param  value Value to be set (single value only) or "" for no value
-   *  @param  checkValue Check 'value'. Not evaluated (here for consistency
-   *          with other setter functions).
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSegmentDescription(const OFString& value,
-                                            const OFBool checkValue = OFTrue);
-
-  /** Set Segment Algorithm Type
-   *  @param  value Value to be set
-   *  @return EC_Normal if successful, an error code otherwise
-   */
-  virtual OFCondition setSegmentAlgorithmType(const DcmSegTypes::E_SegmentAlgoType value);
+    /** Clear all data
+     */
+    virtual void clearData();
 
-protected:
+    /** Read class data from given item
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition read(DcmItem& item);
 
-  /** Read Segment Algorithm Type from given item
-   *  @param  item The item to read from
-   *  @return EC_Normal if reading was successful, error otherwise
-   */
-  virtual OFCondition readSegmentAlgorithmType(DcmItem& item);
+    /** Writes the data from this class to given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition write(DcmItem& item);
 
-  /** Write Segment Algorithm Type to given item
-   *  @param  item The item to write to
-   *  @return EC_Normal if writing was successful, error otherwise
-   */
-  virtual OFCondition writeSegmentAlgorithmType(DcmItem& item);
+    /** Get Segment Label
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSegmentLabel(OFString& value, const signed long pos = 0);
 
+    /** Get Segment Description
+     *  @param  value Reference to variable in which the value should be stored
+     *  @param  pos Index of the value to get (0..vm-1), -1 for all components
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getSegmentDescription(OFString& value, const signed long pos = 0);
 
-private:
+    /** Get Segment Algorithm Type
+     *  @return The algorithm type
+     */
+    virtual DcmSegTypes::E_SegmentAlgoType getSegmentAlgorithmType();
 
-  // Segment Number: (US, VM 1, Type 1): Computed by position in vector of DcmSegmentation
-  // DcmUnsignedShort m_SegmentNumber;
-  /// Segment Number: (LO, VM 1, Type 1)
-  DcmLongString m_SegmentLabel;
+    /** Get reference to General Anatomy Code
+     *  @return Reference to General Anatomy Code
+     */
+    virtual GeneralAnatomyMacro& getGeneralAnatomyCode();
 
-  /// Segment Description: (ST, 1, Type 3)
-  DcmShortText m_SegmentDescription;
+    /** Get Reference to Segmented Property Category Code
+     *  @return Reference to Segmented Property Category Code
+     */
+    virtual CodeSequenceMacro& getSegmentedPropertyCategoryCode();
 
-  /// Segment Algorithm Type: (CS, 1, Type 1)
-  DcmSegTypes::E_SegmentAlgoType m_SegmentAlgorithmType;
+    /** Get Reference to Segmented Property Type Code
+     *  @return Reference to Segmented Property Type Code
+     */
+    virtual CodeSequenceMacro& getSegmentedPropertyTypeCode();
 
-  /// General Anatomy Mandatory Macro
-  GeneralAnatomyMacro m_GeneralAnatomyCode;
+    /** Get Reference to Segmented Property Type Modifier Codes
+     *  @return Reference to Segmented Property Type Modifier Codes
+     */
+    virtual OFVector<CodeSequenceMacro*>& getSegmentedPropertyTypeModifier();
 
-  /// Segment Property Category Code (SQ, 1, 1)
-  /// Baseline CID 7150
-  CodeSequenceMacro m_SegmentedPropertyCategoryCode;
+    /** Set Segment Label
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value' for conformance with VR (LO) and VM (1)
+     *          if enabled
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSegmentLabel(const OFString& value, const OFBool checkValue = OFTrue);
 
-  /// Segmented Property Type Code
-  SegmentedPropertyTypeCodeItem m_SegmentedPropertyType;
+    /** Set Segment Description
+     *  @param  value Value to be set (single value only) or "" for no value
+     *  @param  checkValue Check 'value'. Not evaluated (here for consistency
+     *          with other setter functions).
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSegmentDescription(const OFString& value, const OFBool checkValue = OFTrue);
 
-};
+    /** Set Segment Algorithm Type
+     *  @param  value Value to be set
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition setSegmentAlgorithmType(const DcmSegTypes::E_SegmentAlgoType value);
+
+protected:
+    /** Read Segment Algorithm Type from given item
+     *  @param  item The item to read from
+     *  @return EC_Normal if reading was successful, error otherwise
+     */
+    virtual OFCondition readSegmentAlgorithmType(DcmItem& item);
 
+    /** Write Segment Algorithm Type to given item
+     *  @param  item The item to write to
+     *  @return EC_Normal if writing was successful, error otherwise
+     */
+    virtual OFCondition writeSegmentAlgorithmType(DcmItem& item);
+
+private:
+    // Segment Number: (US, VM 1, Type 1): Computed by position in vector of DcmSegmentation
+    // DcmUnsignedShort m_SegmentNumber;
+    /// Segment Number: (LO, VM 1, Type 1)
+    DcmLongString m_SegmentLabel;
+
+    /// Segment Description: (ST, 1, Type 3)
+    DcmShortText m_SegmentDescription;
+
+    /// Segment Algorithm Type: (CS, 1, Type 1)
+    DcmSegTypes::E_SegmentAlgoType m_SegmentAlgorithmType;
+
+    /// General Anatomy Mandatory Macro
+    GeneralAnatomyMacro m_GeneralAnatomyCode;
+
+    /// Segment Property Category Code (SQ, 1, 1)
+    /// Baseline CID 7150
+    CodeSequenceMacro m_SegmentedPropertyCategoryCode;
+
+    /// Segmented Property Type Code
+    SegmentedPropertyTypeCodeItem m_SegmentedPropertyType;
+};
 
 #endif // SEGTYPES_H
index 91d4cde1d4eec08f1990b962b3e9dd5f8c4a5853..02571a0cfa43acdb387f739f7689d86eb6db00b7 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -23,6 +23,7 @@
 #define SEGUTILS_H
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmseg/segdef.h"
 #include "dcmtk/dcmseg/segtypes.h"
 
@@ -32,104 +33,93 @@ class DCMTK_DCMSEG_EXPORT DcmSegUtils
 {
 
 public:
+    /** Pack the given segmentation pixel data, provided "unpacked", into
+     *  the packed format expected by DICOM
+     *   @param  pixelData Pixel data in unpacked format
+     *   @param  rows Number of rows in the pixel data
+     *   @param  columns The number of columns in the pixel data
+     *   @return The frame data if successful, NULL if an error occurs
+     */
+    static DcmIODTypes::Frame* packBinaryFrame(const Uint8* pixelData, const Uint16 rows, const Uint16 columns);
 
-  /** Pack the given segmentation pixel data, provided "unpacked", into
-   *  the packed format expected by DICOM
-   *   @param  pixelData Pixel data in unpacked format
-   *   @param  rows Number of rows in the pixel data
-   *   @param  columns The number of columns in the pixel data
-   *   @return The frame data if successful, NULL if an error occurs
-   */
-  static DcmIODTypes::Frame* packBinaryFrame(const Uint8* pixelData,
-                                             const Uint16 rows,
-                                             const Uint16 columns);
-
-  /** Compute the number of bytes required for a binary pixel data frame,
-   *  given the number of pixels
-   *  @param  numPixels The total number of pixels
-   *  @return The number of bytes required to pack the data into a binary
-   *          segmentation frame
-   */
-  static size_t getBytesForBinaryFrame(const size_t& numPixels);
+    /** Compute the number of bytes required for a binary pixel data frame,
+     *  given the number of pixels
+     *  @param  numPixels The total number of pixels
+     *  @return The number of bytes required to pack the data into a binary
+     *          segmentation frame
+     */
+    static size_t getBytesForBinaryFrame(const size_t& numPixels);
 
-  /** Unpacks a binary segmentation frame into a "sparse" pixel data frame where
-   *  every resulting byte represents a single bit of the frame being either
-   *  0 (not set) or 1 (set).
-   *  @param  frame The input buffer with the frame in packed format
-   *  @param  rows The rows of the frame
-   *  @param  cols The cols of the frame
-   *  @return The segmentation frame in unpacked format. NULL in case of error.
-   */
-  static DcmIODTypes::Frame* unpackBinaryFrame(const DcmIODTypes::Frame* frame,
-                                               Uint16 rows,
-                                               Uint16 cols);
+    /** Unpacks a binary segmentation frame into a "sparse" pixel data frame where
+     *  every resulting byte represents a single bit of the frame being either
+     *  0 (not set) or 1 (set).
+     *  @param  frame The input buffer with the frame in packed format
+     *  @param  rows The rows of the frame
+     *  @param  cols The cols of the frame
+     *  @return The segmentation frame in unpacked format. NULL in case of error.
+     */
+    static DcmIODTypes::Frame* unpackBinaryFrame(const DcmIODTypes::Frame* frame, Uint16 rows, Uint16 cols);
 
-  /** Aligns 1 bit per pixel frame data to make the frame start at a
-   *  specific bit position within the first byte. This is used in the context
-   *  that dcmseg holds the frames in memory aligned to exact byte positions,
-   *  while the DICOM encoding might require a frame to start at an arbitrary
-   *  bit position since all (1 bit per pixel) frames are directly concatenated
-   *  one after another (i.e. if one frame does not occupy a number of bits
-   *  dividable by 8, not all frames will be aligned at exact byte positions).
-   *  Note that each byte is filled from the right, i.e. the first pixel will
-   *  represented by the bit at the very right of the first byte, and the 9th
-   *  pixel will be in the very right position of the following byte.
-   *  This is not a regular bit shift operation since the bits from the previous
-   *  frame are on the left of the byte, but must be aligned at the right. The
-   *  current frame starts from the first bit, occupying the unused bits of
-   *  the last frame and then continuing in the next byte at the first bit
-   *  from the left.
-   *  Example for two bit shift:
-   *    Input buffer bytes: hgfedcba 87654321
-   *    Result:   fedcba00 654321hg
-   *    The 00 in the first byte must be handled by the caller (will
-   *    contain the two bits of the previous frame).
-   *    See also dcmseg/tests/tutils.cc for more examples.
-   *  @param  buf The address of the memory buffer to shift
-   *  @param  bufLen The length of the buf memory block in bytes
-   *  @param  numBits The number of bits to shift. Must be 0 <= numBits <= 7.
-   */
-  static void alignFrameOnBitPosition(Uint8* buf,
-                                      size_t bufLen,
-                                      Uint8 numBits);
+    /** Aligns 1 bit per pixel frame data to make the frame start at a
+     *  specific bit position within the first byte. This is used in the context
+     *  that dcmseg holds the frames in memory aligned to exact byte positions,
+     *  while the DICOM encoding might require a frame to start at an arbitrary
+     *  bit position since all (1 bit per pixel) frames are directly concatenated
+     *  one after another (i.e. if one frame does not occupy a number of bits
+     *  dividable by 8, not all frames will be aligned at exact byte positions).
+     *  Note that each byte is filled from the right, i.e. the first pixel will
+     *  represented by the bit at the very right of the first byte, and the 9th
+     *  pixel will be in the very right position of the following byte.
+     *  This is not a regular bit shift operation since the bits from the previous
+     *  frame are on the left of the byte, but must be aligned at the right. The
+     *  current frame starts from the first bit, occupying the unused bits of
+     *  the last frame and then continuing in the next byte at the first bit
+     *  from the left.
+     *  Example for two bit shift:
+     *    Input buffer bytes: hgfedcba 87654321
+     *    Result:   fedcba00 654321hg
+     *    The 00 in the first byte must be handled by the caller (will
+     *    contain the two bits of the previous frame).
+     *    See also dcmseg/tests/tutils.cc for more examples.
+     *  @param  buf The address of the memory buffer to shift
+     *  @param  bufLen The length of the buf memory block in bytes
+     *  @param  numBits The number of bits to shift. Must be 0 <= numBits <= 7.
+     */
+    static void alignFrameOnBitPosition(Uint8* buf, const size_t bufLen, const Uint8 numBits);
 
-  /** Aligns 1 bit per pixel frame data starting at a given bit position in the
-   *  provided buffer with the start of that buffer. This is used to create
-   *  a frame structure where all the bytes (including the first one) only
-   *  contain data from the frame at hand.
-   *  Note that each byte is filled from the right, i.e. the first pixel will
-   *  represented by the bit at the very right of the first byte, and the 9th
-   *  pixel will be in the very right position of the following byte.
-   *  Example:
-   *    3 bytes input buffer: edcbaZYX mlkjihgf utsrqpon
-   *    Result after aligning 3 bits: fghedcba ponmlkji 000utsrq
-   *    The 000 are unused bits and therefore zeroed out in the last byte. Bits
-   *    ZYX will be shifted out which is ok since it does not belong to the
-   *    current frame. See also dcmseg/tests/tutils.cc for more examples.
-   *  @param  buf The address of the memory buffer to shift
-   *  @param  bufLen The length of the buf memory block in bytes
-   *  @param  numBits The number of bits to shift. Must be 0 <= numBits <= 7.
-   */
-  static void alignFrameOnByteBoundary(Uint8* buf,
-                                       size_t bufLen,
-                                       Uint8 numBits);
+    /** Aligns 1 bit per pixel frame data starting at a given bit position in the
+     *  provided buffer with the start of that buffer. This is used to create
+     *  a frame structure where all the bytes (including the first one) only
+     *  contain data from the frame at hand.
+     *  Note that each byte is filled from the right, i.e. the first pixel will
+     *  represented by the bit at the very right of the first byte, and the 9th
+     *  pixel will be in the very right position of the following byte.
+     *  Example:
+     *    3 bytes input buffer: edcbaZYX mlkjihgf utsrqpon
+     *    Result after aligning 3 bits: fghedcba ponmlkji 000utsrq
+     *    The 000 are unused bits and therefore zeroed out in the last byte. Bits
+     *    ZYX will be shifted out which is ok since it does not belong to the
+     *    current frame. See also dcmseg/tests/tutils.cc for more examples.
+     *  @param  buf The address of the memory buffer to shift
+     *  @param  bufLen The length of the buf memory block in bytes
+     *  @param  numBits The number of bits to shift. Must be 0 <= numBits <= 7.
+     */
+    static void alignFrameOnByteBoundary(Uint8* buf, const size_t bufLen, const Uint8 numBits);
 
-  /** Dumps a byte as binary number to a string. Only useful for
-   *  debugging purposes.
-   *  @param  b The byte to dump
-   *  @return A string containing b as a binary number
-   */
-  static OFString debugByte2Bin(Uint8 b);
+    /** Dumps a byte as binary number to a string. Only useful for
+     *  debugging purposes.
+     *  @param  b The byte to dump
+     *  @return A string containing b as a binary number
+     */
+    static OFString debugByte2Bin(Uint8 b);
 
-  /** Dumps a memory block byte for byte to the debug log stream. Only useful
-   * for debugging purposes.
-   *  @param  buffer The address of the memory block to dump
-   *  @param  length The length of memory to be dumped
-   *  @param  what String describing what is dumped.
-   */
-  static void debugDumpBin(Uint8* buffer,
-                           size_t length,
-                           const char* what);
+    /** Dumps a memory block byte for byte to the debug log stream. Only useful
+     * for debugging purposes.
+     *  @param  buffer The address of the memory block to dump
+     *  @param  length The length of memory to be dumped
+     *  @param  what String describing what is dumped.
+     */
+    static void debugDumpBin(Uint8* buffer, size_t length, const char* what);
 };
 
 #endif // SEGUTILS_H
index c3e4e7b18ba11abcb34021ab4928b306e33b231b..230616167d529a5e884d6a8a4131e141c3181fa8 100644 (file)
@@ -7,40 +7,25 @@ segdoc.o: segdoc.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../include/dcmtk/dcmseg/segdoc.h \
- ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodimage.h \
- ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../../ofstd/include/dcmtk/ofstd/ofvriant.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/variant.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/helpers.h \
- ../../ofstd/include/dcmtk/ofstd/ofalign.h \
- ../../ofstd/include/dcmtk/ofstd/ofdiag.h \
- ../../ofstd/include/dcmtk/ofstd/diag/push.def \
- ../../ofstd/include/dcmtk/ofstd/diag/cnvrsn.def \
- ../../ofstd/include/dcmtk/ofstd/diag/vsprfw.def \
- ../../ofstd/include/dcmtk/ofstd/diag/pop.def \
- ../../dcmiod/include/dcmtk/dcmiod/iodcommn.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmfg/include/dcmtk/dcmfg/concatenationcreator.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
  ../../oflog/include/dcmtk/oflog/config/defines.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
  ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
@@ -51,13 +36,9 @@ segdoc.o: segdoc.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../../dcmiod/include/dcmtk/dcmiod/modpatient.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
@@ -65,10 +46,12 @@ segdoc.o: segdoc.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
@@ -85,6 +68,7 @@ segdoc.o: segdoc.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -129,43 +113,66 @@ segdoc.o: segdoc.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
- ../../dcmiod/include/dcmtk/dcmiod/modpatientstudy.h \
- ../../ofstd/include/dcmtk/ofstd/ofoption.h \
- ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgderimg.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgbase.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgtypes.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgfact.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgfracon.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgplanor.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgplanpo.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgseg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../include/dcmtk/dcmseg/segdoc.h \
+ ../../dcmfg/include/dcmtk/dcmfg/concatenationloader.h \
+ ../../ofstd/include/dcmtk/ofstd/oftuple.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdiag.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/push.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/mmtag.def \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefrd.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuple.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/pop.def \
+ ../../dcmfg/include/dcmtk/dcmfg/fginterface.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodimage.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodcommn.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h \
  ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
- ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
  ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modpatient.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modpatientstudy.h \
+ ../../ofstd/include/dcmtk/ofstd/ofoption.h \
+ ../../ofstd/include/dcmtk/ofstd/ofalign.h \
  ../../dcmiod/include/dcmtk/dcmiod/modsopcommon.h \
- ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h \
  ../../dcmiod/include/dcmtk/dcmiod/modgeneralimage.h \
  ../../dcmiod/include/dcmtk/dcmiod/modimagepixelvariant.h \
  ../../dcmiod/include/dcmtk/dcmiod/modimagepixelbase.h \
- ../../dcmiod/include/dcmtk/dcmiod/modimagepixel.h \
- ../../dcmiod/include/dcmtk/dcmiod/modsegmentationseries.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvriant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/variant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/helpers.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/cnvrsn.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/vsprfw.def \
  ../../dcmiod/include/dcmtk/dcmiod/modenhequipment.h \
- ../../dcmiod/include/dcmtk/dcmiod/modmultiframefg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixel.h \
  ../../dcmiod/include/dcmtk/dcmiod/modmultiframedimension.h \
- ../../dcmfg/include/dcmtk/dcmfg/fginterface.h \
- ../../dcmfg/include/dcmtk/dcmfg/fgtypes.h \
- ../../dcmfg/include/dcmtk/dcmfg/fgdefine.h \
- ../../dcmfg/include/dcmtk/dcmfg/fg.h \
- ../../dcmfg/include/dcmtk/dcmfg/fgbase.h \
- ../../dcmfg/include/dcmtk/dcmfg/fgfracon.h \
- ../include/dcmtk/dcmseg/segtypes.h ../include/dcmtk/dcmseg/segdef.h \
- ../include/dcmtk/dcmseg/segment.h ../include/dcmtk/dcmseg/segutils.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../dcmfg/include/dcmtk/dcmfg/fgseg.h \
- ../../dcmfg/include/dcmtk/dcmfg/fgplanpo.h \
- ../../dcmfg/include/dcmtk/dcmfg/fgplanor.h \
- ../../dcmfg/include/dcmtk/dcmfg/fgfact.h \
- ../../dcmfg/include/dcmtk/dcmfg/fgderimg.h
+ ../../dcmiod/include/dcmtk/dcmiod/modmultiframefg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modsegmentationseries.h \
+ ../include/dcmtk/dcmseg/segdef.h ../include/dcmtk/dcmseg/segtypes.h \
+ ../include/dcmtk/dcmseg/segment.h ../include/dcmtk/dcmseg/segutils.h
 segment.o: segment.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
@@ -173,14 +180,13 @@ segment.o: segment.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -206,32 +212,31 @@ segment.o: segment.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../include/dcmtk/dcmseg/segment.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../include/dcmtk/dcmseg/segdoc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmfg/include/dcmtk/dcmfg/concatenationcreator.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
@@ -249,7 +254,6 @@ segment.o: segment.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
@@ -259,7 +263,6 @@ segment.o: segment.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
@@ -275,6 +278,7 @@ segment.o: segment.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
@@ -285,44 +289,50 @@ segment.o: segment.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
- ../include/dcmtk/dcmseg/segtypes.h ../include/dcmtk/dcmseg/segdef.h \
- ../include/dcmtk/dcmseg/segdoc.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodimage.h \
- ../../ofstd/include/dcmtk/ofstd/ofvriant.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/variant.h \
- ../../ofstd/include/dcmtk/ofstd/variadic/helpers.h \
- ../../ofstd/include/dcmtk/ofstd/ofalign.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmfg/include/dcmtk/dcmfg/concatenationloader.h \
+ ../../ofstd/include/dcmtk/ofstd/oftuple.h \
  ../../ofstd/include/dcmtk/ofstd/ofdiag.h \
  ../../ofstd/include/dcmtk/ofstd/diag/push.def \
- ../../ofstd/include/dcmtk/ofstd/diag/cnvrsn.def \
- ../../ofstd/include/dcmtk/ofstd/diag/vsprfw.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/mmtag.def \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefrd.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuple.h \
  ../../ofstd/include/dcmtk/ofstd/diag/pop.def \
+ ../../dcmfg/include/dcmtk/dcmfg/fgfracon.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgbase.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fginterface.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodimage.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodcommn.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
  ../../dcmiod/include/dcmtk/dcmiod/modpatient.h \
  ../../dcmiod/include/dcmtk/dcmiod/modpatientstudy.h \
  ../../ofstd/include/dcmtk/ofstd/ofoption.h \
- ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
- ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
- ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
- ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
+ ../../ofstd/include/dcmtk/ofstd/ofalign.h \
  ../../dcmiod/include/dcmtk/dcmiod/modsopcommon.h \
- ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h \
  ../../dcmiod/include/dcmtk/dcmiod/modgeneralimage.h \
  ../../dcmiod/include/dcmtk/dcmiod/modimagepixelvariant.h \
  ../../dcmiod/include/dcmtk/dcmiod/modimagepixelbase.h \
- ../../dcmiod/include/dcmtk/dcmiod/modimagepixel.h \
- ../../dcmiod/include/dcmtk/dcmiod/modsegmentationseries.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvriant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/variant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/helpers.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/cnvrsn.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/vsprfw.def \
  ../../dcmiod/include/dcmtk/dcmiod/modenhequipment.h \
- ../../dcmiod/include/dcmtk/dcmiod/modmultiframefg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixel.h \
  ../../dcmiod/include/dcmtk/dcmiod/modmultiframedimension.h \
- ../../dcmfg/include/dcmtk/dcmfg/fginterface.h \
- ../../dcmfg/include/dcmtk/dcmfg/fgtypes.h \
- ../../dcmfg/include/dcmtk/dcmfg/fgdefine.h \
- ../../dcmfg/include/dcmtk/dcmfg/fg.h \
- ../../dcmfg/include/dcmtk/dcmfg/fgbase.h \
- ../../dcmfg/include/dcmtk/dcmfg/fgfracon.h
+ ../../dcmiod/include/dcmtk/dcmiod/modmultiframefg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modsegmentationseries.h \
+ ../include/dcmtk/dcmseg/segdef.h ../include/dcmtk/dcmseg/segtypes.h \
+ ../include/dcmtk/dcmseg/segment.h
 segtypes.o: segtypes.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
@@ -334,13 +344,8 @@ segtypes.o: segtypes.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -355,6 +360,7 @@ segtypes.o: segtypes.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
  ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
@@ -366,42 +372,38 @@ segtypes.o: segtypes.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -412,9 +414,11 @@ segtypes.o: segtypes.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
@@ -444,15 +448,33 @@ segtypes.o: segtypes.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
  ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
  ../include/dcmtk/dcmseg/segtypes.h ../include/dcmtk/dcmseg/segdef.h
 segutils.o: segutils.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/dcmseg/segutils.h ../include/dcmtk/dcmseg/segdef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
- ../include/dcmtk/dcmseg/segtypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
@@ -460,16 +482,12 @@ segutils.o: segutils.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
  ../../oflog/include/dcmtk/oflog/loglevel.h \
  ../../ofstd/include/dcmtk/ofstd/ofvector.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
- ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../oflog/include/dcmtk/oflog/tstring.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../oflog/include/dcmtk/oflog/tchar.h \
  ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
  ../../oflog/include/dcmtk/oflog/appender.h \
  ../../ofstd/include/dcmtk/ofstd/ofmem.h \
  ../../ofstd/include/dcmtk/ofstd/ofutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
  ../../oflog/include/dcmtk/oflog/layout.h \
  ../../oflog/include/dcmtk/oflog/streams.h \
@@ -481,44 +499,42 @@ segutils.o: segutils.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
- ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../include/dcmtk/dcmseg/segdef.h ../include/dcmtk/dcmseg/segutils.h \
+ ../include/dcmtk/dcmseg/segtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -529,11 +545,9 @@ segutils.o: segutils.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
@@ -563,8 +577,4 @@ segutils.o: segutils.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
  ../../dcmiod/include/dcmtk/dcmiod/modbase.h
index 482c93195d3c3c2803d09bc3f6a0ba9e4d0129e0..1489d6779bd52f20cdc52ac162c0340d9d64cbee 100644 (file)
  *  Purpose: Class representing a Segmentation object
  *
  */
+
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcuid.h"
+#include "dcmtk/dcmfg/concatenationcreator.h"
+#include "dcmtk/dcmfg/fgderimg.h"
+#include "dcmtk/dcmfg/fgfact.h"
+#include "dcmtk/dcmfg/fgfracon.h"
+#include "dcmtk/dcmfg/fgplanor.h"
+#include "dcmtk/dcmfg/fgplanpo.h"
+#include "dcmtk/dcmfg/fgseg.h"
+#include "dcmtk/dcmiod/iodutil.h"
 #include "dcmtk/dcmseg/segdoc.h"
 #include "dcmtk/dcmseg/segment.h"
 #include "dcmtk/dcmseg/segutils.h"
-#include "dcmtk/dcmiod/iodutil.h"
-#include "dcmtk/dcmfg/fgseg.h"
-#include "dcmtk/dcmfg/fgplanpo.h"
-#include "dcmtk/dcmfg/fgplanor.h"
-#include "dcmtk/dcmfg/fgfracon.h"
-#include "dcmtk/dcmfg/fgfact.h"
-#include "dcmtk/dcmfg/fgderimg.h"
 
 // default constructor (protected, instance creation via create() function)
 DcmSegmentation::DcmSegmentation()
-: DcmSegmentation::IODImage(OFin_place<IODImagePixelModule<Uint8> >),
-  m_SegmentationSeries(DcmSegmentation::IODImage::getData(), DcmSegmentation::IODImage::getRules()),
-  m_EnhancedGeneralEquipmentModule(DcmSegmentation::IODImage::getData(), DcmSegmentation::IODImage::getRules()),
-  m_FG(DcmSegmentation::IODImage::getData(), DcmSegmentation::IODImage::getRules()),
-  m_DimensionModule(DcmSegmentation::IODImage::getData(), DcmSegmentation::IODImage::getRules()),
-  m_Frames(),
-  m_ImageType("DERIVED\\PRIMARY"),
-  m_ContentIdentificationMacro(),
-  m_SegmentationType(DcmSegTypes::ST_BINARY),
-  m_SegmentationFractionalType(DcmSegTypes::SFT_OCCUPANCY),
-  m_MaximumFractionalValue(DCM_MaximumFractionalValue),
-  m_Segments(),
-  m_FGInterface()
+    : DcmSegmentation::IODImage(OFin_place<IODImagePixelModule<Uint8> >)
+    , m_SegmentationSeries(DcmSegmentation::IODImage::getData(), DcmSegmentation::IODImage::getRules())
+    , m_EnhancedGeneralEquipmentModule(DcmSegmentation::IODImage::getData(), DcmSegmentation::IODImage::getRules())
+    , m_FG(DcmSegmentation::IODImage::getData(), DcmSegmentation::IODImage::getRules())
+    , m_DimensionModule(DcmSegmentation::IODImage::getData(), DcmSegmentation::IODImage::getRules())
+    , m_Frames()
+    , m_ImageType("DERIVED\\PRIMARY")
+    , m_ContentIdentificationMacro()
+    , m_SegmentationType(DcmSegTypes::ST_BINARY)
+    , m_SegmentationFractionalType(DcmSegTypes::SFT_OCCUPANCY)
+    , m_MaximumFractionalValue(DCM_MaximumFractionalValue)
+    , m_Segments()
+    , m_FGInterface()
 {
-  DcmSegmentation::initIODRules();
+    DcmSegmentation::initIODRules();
 }
 
-
 void DcmSegmentation::initIODRules()
 {
-  // ------------ Segmentation Image Module -------------
-
-  // Partly overrides rules from General Image Module
-  getRules()->addRule(new IODRule(DCM_ImageType, "2","1", "SegmentationImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
-  getRules()->addRule(new IODRule(DCM_SegmentationType, "1","1", "SegmentationImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
-  getRules()->addRule(new IODRule(DCM_SegmentationFractionalType, "1","1C", "SegmentationImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
-  getRules()->addRule(new IODRule(DCM_MaximumFractionalValue, "1","1C", "SegmentationImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
-
-  // Re-use General Image Module instead of Segmentation Image Module
-  getRules()->addRule(new IODRule(DCM_LossyImageCompression, "1","1", "GeneralImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
-  getRules()->addRule(new IODRule(DCM_LossyImageCompressionMethod, "1-n", "1C", "GeneralImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
-  getRules()->addRule(new IODRule(DCM_LossyImageCompressionRatio, "1-n","1C", "GeneralImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
-
-  // Override rule from General Series Module
-  getRules()->addRule(new IODRule(DCM_ReferencedPerformedProcedureStepSequence, "1","1C", "SegmentationSeriesModule", DcmIODTypes::IE_SERIES), OFTrue);
-  getRules()->addRule(new IODRule(DCM_SeriesNumber, "1","1", "SegmentationSeriesModule", DcmIODTypes::IE_SERIES), OFTrue);
-
-  // Instance Number is also used within Content Identification Macro, disable it there
-  m_ContentIdentificationMacro.getIODRules().deleteRule(DCM_InstanceNumber);
+    // ------------ Segmentation Image Module -------------
+
+    // Partly overrides rules from General Image Module
+    getRules()->addRule(new IODRule(DCM_ImageType, "2", "1", "SegmentationImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
+    getRules()->addRule(new IODRule(DCM_SegmentationType, "1", "1", "SegmentationImageModule", DcmIODTypes::IE_IMAGE),
+                        OFTrue);
+    getRules()->addRule(
+        new IODRule(DCM_SegmentationFractionalType, "1", "1C", "SegmentationImageModule", DcmIODTypes::IE_IMAGE),
+        OFTrue);
+    getRules()->addRule(
+        new IODRule(DCM_MaximumFractionalValue, "1", "1C", "SegmentationImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
+
+    // Re-use General Image Module instead of Segmentation Image Module
+    getRules()->addRule(new IODRule(DCM_LossyImageCompression, "1", "1", "GeneralImageModule", DcmIODTypes::IE_IMAGE),
+                        OFTrue);
+    getRules()->addRule(
+        new IODRule(DCM_LossyImageCompressionMethod, "1-n", "1C", "GeneralImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
+    getRules()->addRule(
+        new IODRule(DCM_LossyImageCompressionRatio, "1-n", "1C", "GeneralImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
+
+    // Override rule from General Series Module
+    getRules()->addRule(new IODRule(DCM_ReferencedPerformedProcedureStepSequence,
+                                    "1",
+                                    "1C",
+                                    "SegmentationSeriesModule",
+                                    DcmIODTypes::IE_SERIES),
+                        OFTrue);
+    getRules()->addRule(new IODRule(DCM_SeriesNumber, "1", "1", "SegmentationSeriesModule", DcmIODTypes::IE_SERIES),
+                        OFTrue);
+
+    // Instance Number is also used within Content Identification Macro, disable it there
+    m_ContentIdentificationMacro.getIODRules().deleteRule(DCM_InstanceNumber);
 }
 
-
 DcmSegmentation::~DcmSegmentation()
 {
-  clearData();
+    clearData();
 }
 
-
 // static method for loading segmentation objects
-OFCondition DcmSegmentation::loadFile(const OFString& filename,
-                                      DcmSegmentation*& segmentation)
+OFCondition DcmSegmentation::loadFile(const OFString& filename, DcmSegmentation*& segmentation)
 {
-  DcmFileFormat dcmff;
-  DcmDataset *dataset = NULL;
-  OFCondition result = loadFile(dcmff, filename, dataset);
-  if (result.bad())
-    return result;
+    DcmFileFormat dcmff;
+    DcmDataset* dataset = NULL;
+    OFCondition result  = loadFile(dcmff, filename, dataset);
+    if (result.bad())
+        return result;
 
-  return loadDataset(*dataset, segmentation);
+    return loadDataset(*dataset, segmentation);
 }
 
-
 // static method for loading segmentation objects
-OFCondition DcmSegmentation::loadDataset(DcmDataset& dataset,
-                                         DcmSegmentation*& segmentation)
+OFCondition DcmSegmentation::loadDataset(DcmDataset& dataset, DcmSegmentation*& segmentation)
 {
-  OFCondition result = DcmSegmentation::decompress(dataset);
-  if (result.bad())
-    return result;
-
-  segmentation = new DcmSegmentation();
-  if (segmentation == NULL)
-  {
-    return EC_MemoryExhausted;
-  }
+    segmentation       = NULL;
+    OFCondition result = DcmSegmentation::decompress(dataset);
+    if (result.bad())
+        return result;
 
-  return segmentation->read(dataset);
+    DcmSegmentation* temp = new DcmSegmentation();
+    if (temp == NULL)
+    {
+        return EC_MemoryExhausted;
+    }
 
+    result = temp->read(dataset);
+    if (result.good())
+    {
+        segmentation = temp;
+    }
+    else
+    {
+        delete segmentation;
+    }
+    return result;
 }
 
+OFCondition DcmSegmentation::loadConcatenation(ConcatenationLoader& cl,
+                                               const OFString& concatenationUID,
+                                               DcmSegmentation*& segmentation)
+{
+    DcmDataset dset;
+    segmentation = NULL;
+    OFVector<DcmIODTypes::Frame*> frames;
+    OFCondition result = cl.load(concatenationUID, &dset, frames);
+    if (result.good())
+    {
+        segmentation = new DcmSegmentation();
+        if (segmentation)
+        {
+            result = segmentation->readWithoutPixelData(dset);
+            if (result.good())
+            {
+                segmentation->m_Frames = frames;
+            }
+        }
+        else
+        {
+            result = EC_MemoryExhausted;
+        }
+    }
+    if (result.bad())
+    {
+        DcmIODUtil::freeContainer(frames);
+        delete segmentation;
+    }
+    return result;
+}
 
 OFCondition DcmSegmentation::createBinarySegmentation(DcmSegmentation*& segmentation,
                                                       const Uint16 rows,
@@ -121,16 +171,15 @@ OFCondition DcmSegmentation::createBinarySegmentation(DcmSegmentation*& segmenta
                                                       const ContentIdentificationMacro& contentIdentification)
 {
 
-  OFCondition result = createCommon(segmentation, rows, columns, equipmentInfo, contentIdentification);
-  if (result.bad())
-    return result;
+    OFCondition result = createCommon(segmentation, rows, columns, equipmentInfo, contentIdentification);
+    if (result.bad())
+        return result;
 
-  segmentation->m_SegmentationType = DcmSegTypes::ST_BINARY;
+    segmentation->m_SegmentationType = DcmSegTypes::ST_BINARY;
 
-  return result;
+    return result;
 }
 
-
 OFCondition DcmSegmentation::createFractionalSegmentation(DcmSegmentation*& segmentation,
                                                           const Uint16 rows,
                                                           const Uint16 columns,
@@ -139,475 +188,498 @@ OFCondition DcmSegmentation::createFractionalSegmentation(DcmSegmentation*& segm
                                                           const IODGeneralEquipmentModule::EquipmentInfo& equipmentInfo,
                                                           const ContentIdentificationMacro& contentIdentification)
 {
-  OFCondition result = createCommon(segmentation, rows, columns, equipmentInfo, contentIdentification);
-  if (result.bad())
-    return result;
+    OFCondition result = createCommon(segmentation, rows, columns, equipmentInfo, contentIdentification);
+    if (result.bad())
+        return result;
 
-  segmentation->m_SegmentationType = DcmSegTypes::ST_FRACTIONAL;
-  segmentation->m_SegmentationFractionalType = fractType;
-  segmentation->m_MaximumFractionalValue.putUint16(maxFractionalValue);
+    segmentation->m_SegmentationType           = DcmSegTypes::ST_FRACTIONAL;
+    segmentation->m_SegmentationFractionalType = fractType;
+    segmentation->m_MaximumFractionalValue.putUint16(maxFractionalValue);
 
-  return result;
+    return result;
 }
 
-
 OFCondition DcmSegmentation::createCommon(DcmSegmentation*& segmentation,
                                           const Uint16 rows,
                                           const Uint16 columns,
                                           const IODGeneralEquipmentModule::EquipmentInfo& equipmentInfo,
                                           const ContentIdentificationMacro& contentIdentification)
 {
-  if ( (rows == 0) || (columns == 0) )
-  {
-    DCMSEG_ERROR("Segmentation must have at least 1 row and 1 column");
-    return EC_IllegalParameter;
-  }
-
-  segmentation = new DcmSegmentation();
-  if (segmentation == NULL)
-    return EC_MemoryExhausted;
-
-  segmentation->getImagePixel().setRows(rows);
-  segmentation->getImagePixel().setColumns(columns);
-
-  OFCondition result = segmentation->setContentIdentification(contentIdentification);
-  if (result.good())
-  {
-    OFString tempstr;
-    contentIdentification.getInstanceNumber(tempstr);
-    result = segmentation->getGeneralImage().setInstanceNumber(tempstr);
-    if (result.bad())
+    if ((rows == 0) || (columns == 0))
     {
-      delete segmentation;
-      segmentation = NULL;
-      return EC_InvalidValue;
+        DCMSEG_ERROR("Segmentation must have at least 1 row and 1 column");
+        return EC_IllegalParameter;
     }
 
-    DcmIODUtil::setContentDateAndTimeNow(segmentation->getGeneralImage());
-    result = segmentation->setEquipmentInfo(equipmentInfo, OFTrue /* check */);
-  }
+    segmentation = new DcmSegmentation();
+    if (segmentation == NULL)
+        return EC_MemoryExhausted;
 
-  if (result.bad())
-  {
-    delete segmentation;
-    segmentation = NULL;
-  }
+    segmentation->getImagePixel().setRows(rows);
+    segmentation->getImagePixel().setColumns(columns);
 
-  return result;
-}
+    OFCondition result = segmentation->setContentIdentification(contentIdentification);
+    if (result.good())
+    {
+        OFString tempstr;
+        contentIdentification.getInstanceNumber(tempstr);
+        result = segmentation->getGeneralImage().setInstanceNumber(tempstr);
+        if (result.bad())
+        {
+            delete segmentation;
+            segmentation = NULL;
+            return EC_InvalidValue;
+        }
 
+        DcmIODUtil::setContentDateAndTimeNow(segmentation->getGeneralImage());
+        result = segmentation->setEquipmentInfo(equipmentInfo, OFTrue /* check */);
+    }
 
-FGDerivationImage* DcmSegmentation::createDerivationImageFG(const OFVector< ImageSOPInstanceReferenceMacro >& derivationImages,
-                                                            const OFString& derivationDescription)
-{
-  CodeSequenceMacro derivationCode("113076", "DCM", "Segmentation");
-  CodeSequenceMacro purpose("121322", "DCM", "Source Image for Image Processing Operation");
-  return FGDerivationImage::createMinimal(derivationImages,
-                                          derivationDescription,
-                                          derivationCode,
-                                          purpose);
+    if (result.bad())
+    {
+        delete segmentation;
+        segmentation = NULL;
+    }
+
+    return result;
 }
 
+FGDerivationImage*
+DcmSegmentation::createDerivationImageFG(const OFVector<ImageSOPInstanceReferenceMacro>& derivationImages,
+                                         const OFString& derivationDescription)
+{
+    CodeSequenceMacro derivationCode("113076", "DCM", "Segmentation");
+    CodeSequenceMacro purpose("121322", "DCM", "Source Image for Image Processing Operation");
+    return FGDerivationImage::createMinimal(derivationImages, derivationDescription, derivationCode, purpose);
+}
 
-OFCondition DcmSegmentation::read(DcmItem &dataset)
+OFCondition DcmSegmentation::read(DcmItemdataset)
 {
 
-  OFString sopClass;
-  if (DcmIODUtil::checkSOPClass(&dataset, UID_SegmentationStorage, sopClass).bad())
-  {
-    DCMSEG_ERROR("Given file does not seem to be a segmentation storage object since SOP class is: " << sopClass);
-    return IOD_EC_WrongSOPClass;
-  }
+    OFCondition result = readWithoutPixelData(dataset);
+    if (result.good())
+        result = readFrames(dataset);
+    return result;
+}
 
-  // Read attributes in base classes
-  DcmSegmentation::IODImage::read(dataset);
+OFCondition DcmSegmentation::readWithoutPixelData(DcmItem& dataset)
+{
+    OFString sopClass;
+    if (DcmIODUtil::checkSOPClass(&dataset, UID_SegmentationStorage, sopClass).bad())
+    {
+        DCMSEG_ERROR("Given file does not seem to be a segmentation storage object since SOP class is: " << sopClass);
+        return IOD_EC_WrongSOPClass;
+    }
 
-  // Read Segmentation Series Module
-  m_SegmentationSeries.read(dataset);
+    // Read attributes in base classes
+    DcmSegmentation::IODImage::read(dataset);
 
-  // Read Enhanced General Equipment (i.e. make sure all type 1 elements are
-  // there, which is not checked in General Equipment Module being part of
-  // DcmIODImage.
-  m_EnhancedGeneralEquipmentModule.read(dataset);
+    // Read Segmentation Series Module
+    m_SegmentationSeries.read(dataset);
 
-  // Read functional groups module
-  m_FG.read(dataset);
+    // Read Enhanced General Equipment (i.e. make sure all type 1 elements are
+    // there, which is not checked in General Equipment Module being part of
+    // DcmIODImage.
+    m_EnhancedGeneralEquipmentModule.read(dataset);
 
-  // Read functional groups itself
-  m_FGInterface.read(dataset);
+    // Read functional groups module
+    m_FG.read(dataset);
 
-  // Read dimension information
-  m_DimensionModule.read(dataset);
+    // Read functional groups itself
+    m_FGInterface.read(dataset);
 
-  readSegmentationType(dataset);
+    // Read dimension information
+    m_DimensionModule.read(dataset);
 
-  readSegments(dataset);
+    readSegmentationType(dataset);
 
-  readFrames(dataset);
+    readSegments(dataset);
 
-  readSegmentationFractionalType(dataset);
+    readSegmentationFractionalType(dataset);
 
-  m_ContentIdentificationMacro.read(dataset);
+    m_ContentIdentificationMacro.read(dataset);
 
-  // Read specific segmentation elements
-  DcmIODUtil::getAndCheckElementFromDataset(dataset, m_MaximumFractionalValue, getRules()->getByTag(DCM_MaximumFractionalValue));
+    // Read specific segmentation elements
+    DcmIODUtil::getAndCheckElementFromDataset(
+        dataset, m_MaximumFractionalValue, getRules()->getByTag(DCM_MaximumFractionalValue));
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 void DcmSegmentation::setCheckFGOnWrite(const OFBool doCheck)
 {
-  m_FGInterface.setCheckOnWrite(doCheck);
+    m_FGInterface.setCheckOnWrite(doCheck);
 }
 
-
 OFBool DcmSegmentation::getCheckFGOnWrite()
 {
-  return m_FGInterface.getCheckOnWrite();
+    return m_FGInterface.getCheckOnWrite();
 }
 
-
-OFCondition DcmSegmentation::write(DcmItem &dataset)
+OFCondition DcmSegmentation::writeWithSeparatePixelData(DcmItem& dataset, Uint8*& pixData, size_t& pixDataLength)
 {
-  // FGInterface::write() will know whether it has to check FG structure
-  // so we do not need to check FG structure here (OFFalse).
-  if (!check(OFFalse))
-  {
-    return IOD_EC_InvalidObject;
-  }
-
-  OFCondition result;
+    // FGInterface::write() will know whether it has to check FG structure
+    // so we do not need to check FG structure here (OFFalse).
+    if (!check(OFFalse))
+    {
+        return IOD_EC_InvalidObject;
+    }
 
-  // -- Set constant default values written by external modules --
-  getGeneralImage().setLossyImageCompression("00");
-  getGeneralImage().setImageType(m_ImageType);
-  getSOPCommon().setSOPClassUID(UID_SegmentationStorage);
+    OFCondition result;
 
-  // -- Extra Study level data --
+    // -- Set constant default values written by external modules --
+    getGeneralImage().setLossyImageCompression("00");
+    getGeneralImage().setImageType(m_ImageType);
+    getSOPCommon().setSOPClassUID(UID_SegmentationStorage);
 
-  // Enhanced Equipment Module
-  if (result.good()) result = m_EnhancedGeneralEquipmentModule.write(dataset);
+    // -- Extra Study level data --
 
-  // -- Extra Series level data --
+    // Enhanced Equipment Module
+    if (result.good())
+        result = m_EnhancedGeneralEquipmentModule.write(dataset);
 
-  // Write segmentation-specific series level attribute (Segmentation Series Module)
-  if (result.good()) result = m_SegmentationSeries.write(dataset);
+    // -- Extra Series level data --
 
-  // -- Extra Image level data --
+    // Write segmentation-specific series level attribute (Segmentation Series Module)
+    if (result.good())
+        result = m_SegmentationSeries.write(dataset);
 
-  // Write Multi-Frame Functional Groups Module
-  if (result.good()) result = writeMultiFrameFunctionalGroupsModule(dataset);
+    // -- Extra Image level data --
 
-  // Write Multi-Frame Dimension Module
-  if (result.good()) result = writeMultiFrameDimensionModule(dataset);
+    // Write Multi-Frame Functional Groups Module
+    if (result.good())
+        result = writeMultiFrameFunctionalGroupsModule(dataset);
 
-  // Write segmentation image module and image pixel module
-  if (result.good()) result = writeSegmentationImageModule(dataset);
+    // Write Multi-Frame Dimension Module
+    if (result.good())
+        result = writeMultiFrameDimensionModule(dataset);
 
-  // -- Write common multi frame image IOD attributes --
+    // Write segmentation image module and image pixel module
+    if (result.good())
+        result = writeSegmentationImageModule(dataset);
+
+    // -- Write common multi frame image IOD attributes --
+
+    // Patient Module
+    // General Study Module
+    // General Series Module
+    // Frame of Reference Module
+    // General Equipment Module
+    // General Image Module
+    // Multi-frame Functional Groups Module (except functional groups itself)
+    // SOP Common Module
+    // Common Instance Reference Module
+    if (result.good())
+        result = DcmSegmentation::IODImage::write(dataset);
 
-  // Patient Module
-  // General Study Module
-  // General Series Module
-  // Frame of Reference Module
-  // General Equipment Module
-  // General Image Module
-  // Multi-frame Functional Groups Module (except functional groups itself)
-  // SOP Common Module
-  // Common Instance Reference Module
-  if (result.good()) result = DcmSegmentation::IODImage::write(dataset);
+    // Write frame pixel data
+    if (result.good())
+    {
+        Uint32 numFrames = DcmIODUtil::limitMaxFrames(
+            m_Frames.size(), "More than 2147483647 frames provided, will only write 2147483647");
+        Uint16 rows, cols;
+        rows = cols = 0;
+        getImagePixel().getRows(rows);
+        getImagePixel().getColumns(cols);
+        result = getTotalBytesRequired(rows, cols, numFrames, pixDataLength);
+        if (result.bad())
+            return result;
+
+        pixData = new Uint8[pixDataLength];
+        if (!pixData)
+            return EC_MemoryExhausted;
+
+        if (m_SegmentationType == DcmSegTypes::ST_BINARY)
+            result = writeBinaryFrames(pixData, rows, cols, pixDataLength);
+        else if (m_SegmentationType == DcmSegTypes::ST_FRACTIONAL)
+            result = writeFractionalFrames(pixData, numFrames, pixDataLength);
+        else
+            result = SG_EC_UnknownSegmentationType;
+        if (result.bad())
+        {
+            delete[] pixData;
+            pixData       = NULL;
+            pixDataLength = 0;
+        }
+    }
 
-  return result;
+    return result;
 }
 
-
 FGInterface& DcmSegmentation::getFunctionalGroups()
 {
-  return m_FGInterface;
+    return m_FGInterface;
 }
 
+IODMultiFrameFGModule::ConcatenationInfo& DcmSegmentation::getConcatenationInfo()
+{
+    return m_FG.getConcatenationInfo();
+}
 
 size_t DcmSegmentation::getNumberOfFrames()
 {
-  return m_FGInterface.getNumberOfFrames();
+    return m_FGInterface.getNumberOfFrames();
 }
 
-
-
 size_t DcmSegmentation::getNumberOfSegments()
 {
-  return m_Segments.size();
+    return m_Segments.size();
 }
 
-
 IODGeneralEquipmentModule& DcmSegmentation::getEquipment()
 {
-  return DcmSegmentation::IODImage::getEquipment();
+    return DcmSegmentation::IODImage::getEquipment();
 }
 
-
-IODSegmentationSeriesModule & DcmSegmentation::getSegmentationSeriesModule()
+IODSegmentationSeriesModule& DcmSegmentation::getSegmentationSeriesModule()
 {
-  return m_SegmentationSeries;
+    return m_SegmentationSeries;
 }
 
-
-OFCondition DcmSegmentation::addSegment(DcmSegment* seg,
-                                        Uint16& segmentNumber)
+OFCondition DcmSegmentation::addSegment(DcmSegment* seg, Uint16& segmentNumber)
 {
-  segmentNumber = 0;
-  if (seg == NULL)
-    return EC_IllegalParameter;
-
-  if (m_Segments.size() >= DCM_SEG_MAX_SEGMENTS)
-  {
-    return SG_EC_MaxSegmentsReached;
-  }
-
-  // Casting is safe since we made sure number of segments fits into 16 bit
-  segmentNumber = OFstatic_cast(Uint16, m_Segments.size() + 1);
-  m_Segments.push_back(seg);
-  return EC_Normal;
-}
+    segmentNumber = 0;
+    if (seg == NULL)
+        return EC_IllegalParameter;
 
+    if (m_Segments.size() >= DCM_SEG_MAX_SEGMENTS)
+    {
+        return SG_EC_MaxSegmentsReached;
+    }
+
+    // Casting is safe since we made sure number of segments fits into 16 bit
+    segmentNumber = OFstatic_cast(Uint16, m_Segments.size() + 1);
+    m_Segments.push_back(seg);
+    return EC_Normal;
+}
 
 OFCondition DcmSegmentation::addFrame(Uint8* pixData)
 {
-  OFCondition result;
+    OFCondition result;
 
-  Uint16 rows, cols;
-  if (getImagePixel().getRows(rows).good() && getImagePixel().getColumns(cols).good())
-  {
-    DcmIODTypes::Frame* frame = NULL;
-    if (m_SegmentationType == DcmSegTypes::ST_BINARY)
-    {
-      frame = DcmSegUtils::packBinaryFrame(pixData, rows, cols);
-      if (!frame)
-      {
-        result = IOD_EC_CannotInsertFrame;
-      }
-    }
-    else // fractional
+    Uint16 rows, cols;
+    if (getImagePixel().getRows(rows).good() && getImagePixel().getColumns(cols).good())
     {
-      frame = new DcmIODTypes::Frame();
-      if (frame)
-      {
-        frame->length = rows*cols;
-        frame->pixData = new Uint8[frame->length];
-        if (frame->pixData)
+        DcmIODTypes::Frame* frame = NULL;
+        if (m_SegmentationType == DcmSegTypes::ST_BINARY)
         {
-          memcpy(frame->pixData, pixData, frame->length);
+            frame = DcmSegUtils::packBinaryFrame(pixData, rows, cols);
+            if (!frame)
+            {
+                result = IOD_EC_CannotInsertFrame;
+            }
         }
-        else
+        else // fractional
+        {
+            frame = new DcmIODTypes::Frame();
+            if (frame)
+            {
+                frame->length  = rows * cols;
+                frame->pixData = new Uint8[frame->length];
+                if (frame->pixData)
+                {
+                    memcpy(frame->pixData, pixData, frame->length);
+                }
+                else
+                {
+                    delete frame;
+                    result = EC_MemoryExhausted;
+                }
+            }
+            else
+                result = EC_MemoryExhausted;
+        }
+        if (result.good())
         {
-          delete frame;
-          result = EC_MemoryExhausted;
+            m_Frames.push_back(frame);
         }
-      }
-      else
-        result = EC_MemoryExhausted;
     }
-    if (result.good())
+    else
     {
-      m_Frames.push_back(frame);
+        DCMSEG_ERROR("Cannot add frame since rows and/or columns are unknown");
+        result = IOD_EC_CannotInsertFrame;
     }
-  }
-  else
-  {
-    DCMSEG_ERROR("Cannot add frame since rows and/or columns are unknown");
-    result = IOD_EC_CannotInsertFrame;
-  }
-  return result;
+    return result;
 }
 
-
 SOPInstanceReferenceMacro& DcmSegmentation::getReferencedPPS()
 {
-  return getSeries().getReferencedPPS();
+    return getSeries().getReferencedPPS();
 }
 
-
 const DcmIODTypes::Frame* DcmSegmentation::getFrame(const size_t& frameNo)
 {
-  if (frameNo > m_Frames.size() - 1)
-  {
-    return NULL;
-  }
+    if (frameNo > m_Frames.size() - 1)
+    {
+        return NULL;
+    }
 
-  return m_Frames[frameNo];
+    return m_Frames[frameNo];
 }
 
-
-void DcmSegmentation::getFramesForSegment(const size_t& segmentNumber,
-                                          OFVector<size_t>& frameNumbers)
+void DcmSegmentation::getFramesForSegment(const size_t& segmentNumber, OFVector<size_t>& frameNumbers)
 {
-  size_t numFrames = getNumberOfFrames();
-  for (size_t count = 0; count < numFrames; count++)
-  {
-    FGSegmentation* fg = OFstatic_cast(FGSegmentation*, m_FGInterface.get(OFstatic_cast(Uint32, count), DcmFGTypes::EFG_SEGMENTATION));
-    if (fg == NULL)
+    size_t numFrames = getNumberOfFrames();
+    for (size_t count = 0; count < numFrames; count++)
     {
-      DCMSEG_ERROR("Cannot get segmentation functional group for frame " << count);
-      return;
-    }
-    Uint16 refSeg;
-    if (fg->getReferencedSegmentNumber(refSeg).good())
-    {
-      if (refSeg == segmentNumber)
-      {
-        frameNumbers.push_back(count);
-      }
+        FGSegmentation* fg = OFstatic_cast(
+            FGSegmentation*, m_FGInterface.get(OFstatic_cast(Uint32, count), DcmFGTypes::EFG_SEGMENTATION));
+        if (fg == NULL)
+        {
+            DCMSEG_ERROR("Cannot get segmentation functional group for frame " << count);
+            return;
+        }
+        Uint16 refSeg;
+        if (fg->getReferencedSegmentNumber(refSeg).good())
+        {
+            if (refSeg == segmentNumber)
+            {
+                frameNumbers.push_back(count);
+            }
+        }
     }
-  }
 }
 
-
 OFCondition DcmSegmentation::addForAllFrames(const FGBase& group)
 {
-  return m_FGInterface.addShared(group);
+    return m_FGInterface.addShared(group);
 }
 
-
-OFCondition DcmSegmentation::addFrame(Uint8* pixData,
-                                      const Uint16 segmentNumber,
-                                      const OFVector<FGBase*>& perFrameInformation)
+OFCondition
+DcmSegmentation::addFrame(Uint8* pixData, const Uint16 segmentNumber, const OFVector<FGBase*>& perFrameInformation)
 {
-  Uint32 frameNo = OFstatic_cast(Uint32, m_Frames.size()); // will be the index of the frame (counted from 0)
-  OFCondition result;
-
-  // Check input parameters
-  if ( pixData == NULL )
-  {
-    DCMSEG_ERROR("No pixel data provided or zero length");
-    result = EC_IllegalParameter;
-  }
-  if (segmentNumber > m_Segments.size() )
-  {
-    DCMSEG_ERROR("Cannot add frame: Segment with given number " << segmentNumber << " does not exist");
-    result = SG_EC_NoSuchSegment;
-  }
-  if (result.bad())
-    return result;
+    Uint32 frameNo = OFstatic_cast(Uint32, m_Frames.size()); // will be the index of the frame (counted from 0)
+    OFCondition result;
 
-  OFVector<FGBase*>::const_iterator it = perFrameInformation.begin();
-  while (it != perFrameInformation.end())
-  {
-    result = (*it)->check();
-    if (result.bad())
+    // Check input parameters
+    if (pixData == NULL)
     {
-      DCMSEG_ERROR("Could not add new frame since functional group of type: " << (*it)->getType() << " is invalid: " << result.text());
-      break;
+        DCMSEG_ERROR("No pixel data provided or zero length");
+        result = EC_IllegalParameter;
+    }
+    if (segmentNumber > m_Segments.size())
+    {
+        DCMSEG_ERROR("Cannot add frame: Segment with given number " << segmentNumber << " does not exist");
+        result = SG_EC_NoSuchSegment;
     }
-    result = m_FGInterface.addPerFrame(frameNo, *(*it));
     if (result.bad())
+        return result;
+
+    OFVector<FGBase*>::const_iterator it = perFrameInformation.begin();
+    while (it != perFrameInformation.end())
     {
-      DCMSEG_ERROR("Could not add new frame since functional group of type " << (*it)->getType() << ": " << result.text());
-      break;
+        result = (*it)->check();
+        if (result.bad())
+        {
+            DCMSEG_ERROR("Could not add new frame since functional group of type: "
+                         << (*it)->getType() << " is invalid: " << result.text());
+            break;
+        }
+        result = m_FGInterface.addPerFrame(frameNo, *(*it));
+        if (result.bad())
+        {
+            DCMSEG_ERROR("Could not add new frame since functional group of type " << (*it)->getType() << ": "
+                                                                                   << result.text());
+            break;
+        }
+        it++;
     }
-    it++;
-  }
 
-  // Now also add Segmentation Functional Group
-  if (result.good())
-  {
-    FGSegmentation seg;
-    result = seg.setReferencedSegmentNumber(segmentNumber);
+    // Now also add Segmentation Functional Group
     if (result.good())
     {
-      result = m_FGInterface.addPerFrame(frameNo, seg);
+        FGSegmentation seg;
+        result = seg.setReferencedSegmentNumber(segmentNumber);
+        if (result.good())
+        {
+            result = m_FGInterface.addPerFrame(frameNo, seg);
+        }
+        else
+        {
+            DCMSEG_ERROR("Could not add new frame, invalid segment number " << segmentNumber << ": " << result.text());
+        }
     }
-    else
+
+    // Insert pixel data
+    if (result.good())
     {
-      DCMSEG_ERROR("Could not add new frame, invalid segment number " << segmentNumber << ": " << result.text());
+        result = addFrame(pixData);
     }
-  }
-
-  // Insert pixel data
-  if (result.good())
-  {
-    result = addFrame(pixData);
-  }
 
-  // Cleanup any per-frame groups that might have been inserted and return
-  if (result.bad())
-  {
-    for (OFVector<FGBase*>::const_iterator it2 = perFrameInformation.begin(); it2 != perFrameInformation.end(); it2++ )
+    // Cleanup any per-frame groups that might have been inserted and return
+    if (result.bad())
     {
-      m_FGInterface.deletePerFrame(frameNo, (*it2)->getType());
+        for (OFVector<FGBase*>::const_iterator it2 = perFrameInformation.begin(); it2 != perFrameInformation.end();
+             it2++)
+        {
+            m_FGInterface.deletePerFrame(frameNo, (*it2)->getType());
+        }
     }
-  }
 
-  return result;
+    return result;
 }
 
-
 ContentIdentificationMacro& DcmSegmentation::getContentIdentification()
 {
-  return m_ContentIdentificationMacro;
+    return m_ContentIdentificationMacro;
 }
 
-
 IODMultiframeDimensionModule& DcmSegmentation::getDimensions()
 {
-  return m_DimensionModule;
+    return m_DimensionModule;
 }
 
-
-OFCondition DcmSegmentation::setLossyImageCompressionFlag(const OFString& ratios,
-                                                          const OFString& methods,
-                                                          const OFBool checkValues)
+OFCondition
+DcmSegmentation::setLossyImageCompressionFlag(const OFString& ratios, const OFString& methods, const OFBool checkValues)
 {
-  OFCondition result = getGeneralImage().setLossyImageCompression("01");
-  if (result.good() || !checkValues)
-    result = getGeneralImage().setLossyImageCompressionMethod(methods);
-  if (result.good() || !checkValues)
-    result = getGeneralImage().setLossyImageCompressionRatio(ratios);
+    OFCondition result = getGeneralImage().setLossyImageCompression("01");
+    if (result.good() || !checkValues)
+        result = getGeneralImage().setLossyImageCompressionMethod(methods);
+    if (result.good() || !checkValues)
+        result = getGeneralImage().setLossyImageCompressionRatio(ratios);
 
-  if (checkValues)
-    return result;
-  else
-    return EC_Normal;
+    if (checkValues)
+        return result;
+    else
+        return EC_Normal;
 }
 
-
-OFCondition DcmSegmentation::saveFile(const OFString& filename,
-                                      const E_TransferSyntax writeXfer)
+OFCondition DcmSegmentation::saveFile(const OFString& filename, const E_TransferSyntax writeXfer)
 {
-  if ( (writeXfer != EXS_LittleEndianExplicit)
-    && (writeXfer != EXS_BigEndianExplicit)
-    && (writeXfer != EXS_LittleEndianImplicit)
+    if ((writeXfer != EXS_LittleEndianExplicit) && (writeXfer != EXS_BigEndianExplicit)
+        && (writeXfer != EXS_LittleEndianImplicit)
 #ifdef WITH_ZLIB
-    && (writeXfer != EXS_DeflatedLittleEndianExplicit)
+        && (writeXfer != EXS_DeflatedLittleEndianExplicit)
 #endif
-  )
-  {
-    DcmXfer ts(writeXfer);
+    )
+    {
+        DcmXfer ts(writeXfer);
 #ifdef WITH_ZLIB
-    DCMSEG_ERROR("Cannot write transfer syntax: " << ts.getXferName() << ": Can only write uncompressed or Deflated)");
+        DCMSEG_ERROR("Cannot write transfer syntax: " << ts.getXferName()
+                                                      << ": Can only write uncompressed or Deflated)");
 #else
-    if (writeXfer == EXS_DeflatedLittleEndianExplicit)
+        if (writeXfer == EXS_DeflatedLittleEndianExplicit)
+        {
+            DCMSEG_ERROR("Cannot write transfer syntax: "
+                         << ts.getXferName() << ": Deflate (ZLIB) support disabled, can only write uncompressed");
+        }
+#endif
+        return EC_CannotChangeRepresentation;
+    }
+
+    DcmFileFormat dcmff;
+    OFCondition result = writeDataset(*(dcmff.getDataset()));
+    if (result.good())
     {
-      DCMSEG_ERROR("Cannot write transfer syntax: " << ts.getXferName() << ": Deflate (ZLIB) support disabled, can only write uncompressed");
+        result = dcmff.saveFile(filename.c_str(), writeXfer);
+    }
+    if (result.bad())
+    {
+        DCMSEG_ERROR("Cannot save segmentation document to file " << filename << ": " << result.text());
     }
-#endif
-    return EC_CannotChangeRepresentation;
-  }
-
-  DcmFileFormat dcmff;
-  OFCondition result = write( *(dcmff.getDataset()) );
-  if (result.good())
-  {
-    result = dcmff.saveFile(filename.c_str(), writeXfer);
-  }
-  if (result.bad())
-  {
-    DCMSEG_ERROR("Cannot save segmentation document to file " << filename << ": " << result.text());
-  }
-
-  return result;
-}
 
+    return result;
+}
 
 /* -- Setter for DICOM attributes -- */
 
@@ -615,197 +687,182 @@ OFCondition DcmSegmentation::setEquipmentInfo(const IODGeneralEquipmentModule::E
                                               const OFBool checkValue)
 {
 
-  if (checkValue)
-  {
-    if ( equipmentInfo.m_Manufacturer.empty()
-      || equipmentInfo.m_ManufacturerModelName.empty()
-      || equipmentInfo.m_DeviceSerialNumber.empty()
-      || equipmentInfo.m_SoftwareVersions.empty() )
+    if (checkValue)
     {
-      return EC_InvalidValue;
+        if (equipmentInfo.m_Manufacturer.empty() || equipmentInfo.m_ManufacturerModelName.empty()
+            || equipmentInfo.m_DeviceSerialNumber.empty() || equipmentInfo.m_SoftwareVersions.empty())
+        {
+            return EC_InvalidValue;
+        }
     }
-  }
 
-  OFCondition result = getEquipment().setManufacturer(equipmentInfo.m_Manufacturer, checkValue);
-  if ( result.good() )
-    result = getEquipment().setManufacturerModelName(equipmentInfo.m_ManufacturerModelName, checkValue);
-  if (result.good())
-    result = getEquipment().setDeviceSerialNumber(equipmentInfo.m_DeviceSerialNumber, checkValue);
-  if (result.good())
-    result = getEquipment().setSoftwareVersions(equipmentInfo.m_SoftwareVersions, checkValue);
+    OFCondition result = getEquipment().setManufacturer(equipmentInfo.m_Manufacturer, checkValue);
+    if (result.good())
+        result = getEquipment().setManufacturerModelName(equipmentInfo.m_ManufacturerModelName, checkValue);
+    if (result.good())
+        result = getEquipment().setDeviceSerialNumber(equipmentInfo.m_DeviceSerialNumber, checkValue);
+    if (result.good())
+        result = getEquipment().setSoftwareVersions(equipmentInfo.m_SoftwareVersions, checkValue);
 
-  return result;
+    return result;
 }
 
-
 OFCondition DcmSegmentation::setContentIdentification(const ContentIdentificationMacro& contentIdentification,
                                                       const OFBool checkValue)
 {
-  // Instance Number and Content Label must be filled out, rest can be empty
-  OFCondition result;
-  if (checkValue)
-  {
-    result = OFconst_cast(ContentIdentificationMacro*,&contentIdentification)->check();
-  }
-  if (result.bad())
-    return result;
+    // Instance Number and Content Label must be filled out, rest can be empty
+    OFCondition result;
+    if (checkValue)
+    {
+        result = OFconst_cast(ContentIdentificationMacro*, &contentIdentification)->check();
+    }
+    if (result.bad())
+        return result;
 
-  m_ContentIdentificationMacro = contentIdentification;
+    m_ContentIdentificationMacro = contentIdentification;
 
-  return result;
+    return result;
 }
 
-
-
 /* -- Getter for DICOM attributes -- */
 
 DcmSegment* DcmSegmentation::getSegment(const unsigned int segmentNumber)
 {
-  // check for invalid index
-  if ( (segmentNumber == 0) || (segmentNumber > m_Segments.size()) )
-  {
-    return NULL;
-  }
-
-  // logical segment numbering starts with 1, so subtract 1 for vector index
-  return m_Segments[segmentNumber-1];
-}
+    // check for invalid index
+    if ((segmentNumber == 0) || (segmentNumber > m_Segments.size()))
+    {
+        return NULL;
+    }
 
+    // logical segment numbering starts with 1, so subtract 1 for vector index
+    return m_Segments[segmentNumber - 1];
+}
 
-OFBool DcmSegmentation::getSegmentNumber(const DcmSegment* segment,
-                                         unsigned int& segmentNumber)
+OFBool DcmSegmentation::getSegmentNumber(const DcmSegment* segment, unsigned int& segmentNumber)
 {
-  segmentNumber = 0;
-  size_t max = m_Segments.size();
-  for (size_t count = 0; count < max; count++)
-  {
-    if (m_Segments.at(count) == segment)
-    {
-      // logical segment numbering starts with 1 but vector index with 0
-      segmentNumber = OFstatic_cast(unsigned int, count + 1);
-      return OFTrue;
-    }
-  }
-  // not found
-  return OFFalse;
+    segmentNumber = 0;
+    size_t max    = m_Segments.size();
+    for (size_t count = 0; count < max; count++)
+    {
+        if (m_Segments.at(count) == segment)
+        {
+            // logical segment numbering starts with 1 but vector index with 0
+            segmentNumber = OFstatic_cast(unsigned int, count + 1);
+            return OFTrue;
+        }
+    }
+    // not found
+    return OFFalse;
 }
 
-
-OFCondition DcmSegmentation::getModality(OFString& value,
-                                         const long signed int pos) const
+OFCondition DcmSegmentation::getModality(OFString& value, const long signed int pos) const
 {
-  (void)pos;
-  // Fixed for Segmentations to value "SEG"
-  value = "SEG";
-  return EC_Normal;
+    (void)pos;
+    // Fixed for Segmentations to value "SEG"
+    value = "SEG";
+    return EC_Normal;
 }
 
-
-OFCondition DcmSegmentation::importFromSourceImage(const OFString& filename,
-                                                   const bool takeOverCharset)
+OFCondition DcmSegmentation::importFromSourceImage(const OFString& filename, const bool takeOverCharset)
 {
-  DcmFileFormat dcmff;
-  OFCondition result = dcmff.loadFile(filename);
-  if (result.good())
-  {
-    return importFromSourceImage(*(dcmff.getDataset()), takeOverCharset);
-  }
-  return result;
+    DcmFileFormat dcmff;
+    OFCondition result = dcmff.loadFile(filename);
+    if (result.good())
+    {
+        return importFromSourceImage(*(dcmff.getDataset()), takeOverCharset);
+    }
+    return result;
 }
 
-
-OFCondition DcmSegmentation::importFromSourceImage(DcmItem& dataset,
-                                                   const bool takeOverCharset)
+OFCondition DcmSegmentation::importFromSourceImage(DcmItem& dataset, const bool takeOverCharset)
 {
-  OFString FoR;
-  dataset.findAndGetOFStringArray(DCM_FrameOfReferenceUID, FoR);
-  return DcmIODCommon::importHierarchy(
-    dataset,
-    OFTrue,       // Patient
-    OFTrue,       // Study
-    !FoR.empty(), // Frame of Reference
-    OFFalse,      // Series
-    takeOverCharset);
+    OFString FoR;
+    dataset.findAndGetOFStringArray(DCM_FrameOfReferenceUID, FoR);
+    return DcmIODCommon::importHierarchy(dataset,
+                                         OFTrue,       // Patient
+                                         OFTrue,       // Study
+                                         !FoR.empty(), // Frame of Reference
+                                         OFFalse,      // Series
+                                         takeOverCharset);
 }
 
-
 /* protected functions */
 
 OFCondition DcmSegmentation::writeSegments(DcmItem& item)
 {
-  OFCondition result;
-  DcmIODUtil::writeSubSequence<OFVector<DcmSegment*> >(result, DCM_SegmentSequence, m_Segments, item, "1-n", "1", "SegmentationImageModule");
-  return result;
+    OFCondition result;
+    DcmIODUtil::writeSubSequence<OFVector<DcmSegment*> >(
+        result, DCM_SegmentSequence, m_Segments, item, "1-n", "1", "SegmentationImageModule");
+    return result;
 }
 
-
 OFCondition DcmSegmentation::readSegments(DcmItem& item)
 {
-  return DcmIODUtil::readSubSequence<OFVector<DcmSegment*> >(item, DCM_SegmentSequence, m_Segments, "1-n", "1", "SegmentationImageModule");
+    return DcmIODUtil::readSubSequence<OFVector<DcmSegment*> >(
+        item, DCM_SegmentSequence, m_Segments, "1-n", "1", "SegmentationImageModule");
 }
 
-
 OFCondition DcmSegmentation::readFrames(DcmItem& dataset)
 {
-  OFCondition result;
-  Uint16 allocated, stored, high, spp, pixelRep, rows, cols, numberOfFrames;
-  allocated = stored = high = spp = rows = cols = numberOfFrames = 0;
-  pixelRep = 2; // invalid value for this attribute
-  OFString colorModel;
-
-  /* check the typical image pixel attributes and get correct(ed) values */
-  result = getAndCheckImagePixelAttributes(dataset, allocated, stored, high, spp, pixelRep, rows, cols, numberOfFrames, colorModel);
-  if (result.bad())
-    return result;
+    OFCondition result;
+    Uint16 allocated, stored, high, spp, pixelRep, rows, cols, numberOfFrames;
+    allocated = stored = high = spp = rows = cols = numberOfFrames = 0;
+    pixelRep                                                       = 2; // invalid value for this attribute
+    OFString colorModel;
+
+    /* check the typical image pixel attributes and get correct(ed) values */
+    result = getAndCheckImagePixelAttributes(
+        dataset, allocated, stored, high, spp, pixelRep, rows, cols, numberOfFrames, colorModel);
+    if (result.bad())
+        return result;
 
-  /* Check length of pixel data element */
-  DcmElement* pixelData = NULL;
-  if (dataset.findAndGetElement(DCM_PixelData, pixelData).bad())
-    return IOD_EC_InvalidPixelData;
-  if (!checkPixDataLength(pixelData, rows, cols, numberOfFrames))
-    return IOD_EC_InvalidPixelData;
-
-  /* Get pixel data values */
-  Uint8* pixels = NULL;
-  result = pixelData->getUint8Array(pixels);
-  if (result.bad())
-  {
-    DCMSEG_ERROR("Cannot read pixel data");
-    return result;
-  }
-
-  /* Read all frames into dedicated data structure */
-  size_t pixelsPerFrame = OFstatic_cast(size_t, rows) * cols;
-  if (m_SegmentationType == DcmSegTypes::ST_BINARY)
-  {
-      result = extractFrames(pixels, numberOfFrames, pixelsPerFrame, m_Frames);
-      if (result.bad())
-      {
+    /* Check length of pixel data element */
+    DcmElement* pixelData = NULL;
+    if (dataset.findAndGetElement(DCM_PixelData, pixelData).bad())
+        return IOD_EC_InvalidPixelData;
+    if (!checkPixDataLength(pixelData, rows, cols, numberOfFrames))
+        return IOD_EC_InvalidPixelData;
+
+    /* Get pixel data values */
+    Uint8* pixels = NULL;
+    result        = pixelData->getUint8Array(pixels);
+    if (result.bad())
+    {
+        DCMSEG_ERROR("Cannot read pixel data");
         return result;
     }
-  }
-  else if (m_SegmentationType == DcmSegTypes::ST_FRACTIONAL)
-  {
-    for (size_t count = 0; count < numberOfFrames; count++)
-    {
-      DcmIODTypes::Frame *frame = new DcmIODTypes::Frame();
-      if (!frame) return EC_MemoryExhausted;
-      frame->length = pixelsPerFrame;
-      frame->pixData= new Uint8[pixelsPerFrame];
-      if (!frame->pixData)
-      {
-          delete frame;
-          return EC_MemoryExhausted;
-      }
-      memcpy(frame->pixData, pixels + count* pixelsPerFrame, pixelsPerFrame);
-      m_Frames.push_back(frame);
-    }
-  }
-
-  return result;
-}
 
+    /* Read all frames into dedicated data structure */
+    size_t pixelsPerFrame = OFstatic_cast(size_t, rows) * cols;
+    if (m_SegmentationType == DcmSegTypes::ST_BINARY)
+    {
+        result = DcmIODUtil::extractBinaryFrames(pixels, numberOfFrames, pixelsPerFrame, m_Frames);
+        if (result.bad())
+        {
+            return result;
+        }
+    }
+    else if (m_SegmentationType == DcmSegTypes::ST_FRACTIONAL)
+    {
+        for (size_t count = 0; count < numberOfFrames; count++)
+        {
+            DcmIODTypes::Frame* frame = new DcmIODTypes::Frame();
+            if (!frame)
+                return EC_MemoryExhausted;
+            frame->length  = pixelsPerFrame;
+            frame->pixData = new Uint8[pixelsPerFrame];
+            if (!frame->pixData)
+            {
+                delete frame;
+                return EC_MemoryExhausted;
+            }
+            memcpy(frame->pixData, pixels + count * pixelsPerFrame, pixelsPerFrame);
+            m_Frames.push_back(frame);
+        }
+    }
 
+    return result;
+}
 
 OFCondition DcmSegmentation::getAndCheckImagePixelAttributes(DcmItem& dataset,
                                                              Uint16& allocated,
@@ -818,663 +875,592 @@ OFCondition DcmSegmentation::getAndCheckImagePixelAttributes(DcmItem& dataset,
                                                              Uint16& numberOfFrames,
                                                              OFString& colorModel)
 {
-  OFBool fail = OFFalse;
-  dataset.findAndGetUint16(DCM_BitsAllocated, allocated);
-  dataset.findAndGetUint16(DCM_BitsStored, stored);
-  dataset.findAndGetUint16(DCM_HighBit, high);
-  dataset.findAndGetUint16(DCM_PixelRepresentation, pixelRep);
-  dataset.findAndGetUint16(DCM_SamplesPerPixel, spp);
-  dataset.findAndGetOFStringArray(DCM_PhotometricInterpretation, colorModel);
-
-  /* Rows and Columns */
-  OFCondition result = getImagePixel().getRows(rows);
-  if (result.good())
-    result = getImagePixel().getColumns(cols);
-  if (result.bad())
-  {
-    DCMSEG_ERROR("Cannot find Rows or Columns in dataset");
-    fail = OFTrue;
-  }
-
-  /* Number of Frames */
-  Sint32 numFrames = 0;
-  result = m_FG.getNumberOfFrames(numFrames);
-  if (result.bad())
-  {
-    DCMSEG_ERROR("Number of Frames not set");
-    fail = OFTrue;
-  }
-  else
-  {
-    if ( numFrames < 0 )
-    {
-      DCMSEG_ERROR("Number of Frames must be greater than 0");
-      fail = OFTrue;
+    OFBool fail = OFFalse;
+    dataset.findAndGetUint16(DCM_BitsAllocated, allocated);
+    dataset.findAndGetUint16(DCM_BitsStored, stored);
+    dataset.findAndGetUint16(DCM_HighBit, high);
+    dataset.findAndGetUint16(DCM_PixelRepresentation, pixelRep);
+    dataset.findAndGetUint16(DCM_SamplesPerPixel, spp);
+    dataset.findAndGetOFStringArray(DCM_PhotometricInterpretation, colorModel);
+
+    /* Rows and Columns */
+    OFCondition result = getImagePixel().getRows(rows);
+    if (result.good())
+        result = getImagePixel().getColumns(cols);
+    if (result.bad())
+    {
+        DCMSEG_ERROR("Cannot find Rows or Columns in dataset");
+        fail = OFTrue;
+    }
+
+    /* Number of Frames */
+    Sint32 numFrames = 0;
+    result           = m_FG.getNumberOfFrames(numFrames);
+    if (result.bad())
+    {
+        DCMSEG_ERROR("Number of Frames not set");
+        fail = OFTrue;
     }
     else
     {
-      numberOfFrames = OFstatic_cast(Uint16, numFrames);
-    }
-  }
-
-  Uint16 depth = 0;
-  if (m_SegmentationType == DcmSegTypes::ST_BINARY)
-    depth = 1;
-  else
-    depth = 8;
-
-  if (allocated != depth)
-  {
-    DCMSEG_WARN("Bits Allocated is not set correctly (" << allocated << ", ignored), assuming value " << depth << " as required for " << DcmSegTypes::segtype2OFString(m_SegmentationType) << " segmentation objects");
-    allocated = depth;
-  }
-  if (stored != depth)
-  {
-    DCMSEG_WARN("Bits Stored is not set correctly (" << stored << ", ignored), assuming value " << depth << " as required for " << DcmSegTypes::segtype2OFString(m_SegmentationType) << " segmentation objects");
-    stored = depth;
-  }
-  if (high != depth-1)
-  {
-    DCMSEG_WARN("High Bit is not set correctly (" << high << ", ignored), assuming value " << depth-1 << " as required for " << DcmSegTypes::segtype2OFString(m_SegmentationType) << " segmentation objects");
-    high = depth -1;
-  }
-  if (spp != 1)
-  {
-    DCMSEG_WARN("Samples per Pixel is not set correctly (" << spp << ", ignored), assuming value 1 as required for segmentation objects");
-    spp = 1;
-  }
-  if (pixelRep != 0)
-  {
-    DCMSEG_WARN("Pixel Representation is not set correctly (" << pixelRep << ", ignored), assuming value 0 as required for segmentation objects");
-    pixelRep = 0;
-  }
-  if (colorModel != "MONOCHROME2")
-  {
-    DCMSEG_WARN("Photometric Interpretation is not set correctly (ignored), assuming value MONOCHROME2 as required for segmentation objects");
-    colorModel = "MONOCHROME2";
-  }
-  if (rows == 0)
-  {
-    DCMSEG_ERROR("Rows is not set correctly (0)");
-    fail = OFTrue;
-  }
-  if (cols == 0)
-  {
-    DCMSEG_ERROR("Columns is not set correctly (0)");
-    fail = OFTrue;
-  }
-
-  if (fail)
-    return EC_InvalidValue;
-
-  return EC_Normal;
-}
+        if (numFrames < 0)
+        {
+            DCMSEG_ERROR("Number of Frames must be greater than 0");
+            fail = OFTrue;
+        }
+        else
+        {
+            numberOfFrames = OFstatic_cast(Uint16, numFrames);
+        }
+    }
 
+    Uint16 depth = 0;
+    if (m_SegmentationType == DcmSegTypes::ST_BINARY)
+        depth = 1;
+    else
+        depth = 8;
+
+    if (allocated != depth)
+    {
+        DCMSEG_WARN("Bits Allocated is not set correctly ("
+                    << allocated << ", ignored), assuming value " << depth << " as required for "
+                    << DcmSegTypes::segtype2OFString(m_SegmentationType) << " segmentation objects");
+        allocated = depth;
+    }
+    if (stored != depth)
+    {
+        DCMSEG_WARN("Bits Stored is not set correctly ("
+                    << stored << ", ignored), assuming value " << depth << " as required for "
+                    << DcmSegTypes::segtype2OFString(m_SegmentationType) << " segmentation objects");
+        stored = depth;
+    }
+    if (high != depth - 1)
+    {
+        DCMSEG_WARN("High Bit is not set correctly ("
+                    << high << ", ignored), assuming value " << depth - 1 << " as required for "
+                    << DcmSegTypes::segtype2OFString(m_SegmentationType) << " segmentation objects");
+        high = depth - 1;
+    }
+    if (spp != 1)
+    {
+        DCMSEG_WARN("Samples per Pixel is not set correctly ("
+                    << spp << ", ignored), assuming value 1 as required for segmentation objects");
+        spp = 1;
+    }
+    if (pixelRep != 0)
+    {
+        DCMSEG_WARN("Pixel Representation is not set correctly ("
+                    << pixelRep << ", ignored), assuming value 0 as required for segmentation objects");
+        pixelRep = 0;
+    }
+    if (colorModel != "MONOCHROME2")
+    {
+        DCMSEG_WARN("Photometric Interpretation is not set correctly (ignored), assuming value MONOCHROME2 as required "
+                    "for segmentation objects");
+        colorModel = "MONOCHROME2";
+    }
+    if (rows == 0)
+    {
+        DCMSEG_ERROR("Rows is not set correctly (0)");
+        fail = OFTrue;
+    }
+    if (cols == 0)
+    {
+        DCMSEG_ERROR("Columns is not set correctly (0)");
+        fail = OFTrue;
+    }
+
+    if (fail)
+        return EC_InvalidValue;
+
+    return EC_Normal;
+}
 
 OFCondition DcmSegmentation::writeDataset(DcmItem& dataset)
 {
-  return write(dataset);
+    Uint8* pixData = NULL;
+    size_t pixDataLength;
+    OFCondition result = writeWithSeparatePixelData(dataset, pixData, pixDataLength);
+    if (result.good())
+    {
+        if (pixDataLength <= 4294967294UL)
+        {
+            result = dataset.putAndInsertUint8Array(DCM_PixelData, pixData, OFstatic_cast(unsigned long, pixDataLength));
+        }
+        else
+        {
+            result = FG_EC_PixelDataTooLarge;
+        }
+        delete[] pixData;
+    }
+    return result;
 }
 
+OFCondition DcmSegmentation::writeConcatenation(ConcatenationCreator& cc)
+{
+    Uint8* pixData       = NULL;
+    size_t pixDataLength = 0;
+    DcmItem* item        = new DcmItem();
+    if (!item)
+        return EC_MemoryExhausted;
+    OFCondition result = writeWithSeparatePixelData(*item, pixData, pixDataLength);
+    if (result.good())
+    {
+        result = cc.setCfgInput(item, pixData, pixDataLength, OFTrue /* transfer ownership */);
+    }
+    return result;
+}
 
 OFCondition DcmSegmentation::writeMultiFrameFunctionalGroupsModule(DcmItem& dataset)
 {
-  Uint32 numFrames = DcmIODUtil::limitMaxFrames(m_Frames.size(), "More than 2147483647 frames provided, limiting Number of Frames to 2147483647");
-  m_FG.setNumberOfFrames(numFrames);
-  OFCondition result = m_FG.write(dataset);
-  if (result.good())
-    m_FGInterface.write(dataset);
-  return result;
+    Uint32 numFrames = DcmIODUtil::limitMaxFrames(
+        m_Frames.size(), "More than 2147483647 frames provided, limiting Number of Frames to 2147483647");
+    m_FG.setNumberOfFrames(numFrames);
+    OFCondition result = m_FG.write(dataset);
+    if (result.good())
+        m_FGInterface.write(dataset);
+    return result;
 }
 
-
 OFCondition DcmSegmentation::writeMultiFrameDimensionModule(DcmItem& dataset)
 {
-  OFCondition result = m_DimensionModule.checkDimensions(&dataset);
-  if (result.good())
-  {
-    result = m_DimensionModule.write(dataset);
-  }
-  return result;
+    OFCondition result = m_DimensionModule.checkDimensions(&dataset);
+    if (result.good())
+    {
+        result = m_DimensionModule.write(dataset);
+    }
+    return result;
 }
 
-
-OFCondition DcmSegmentation::writeFractionalFrames(DcmItem& dataset)
+OFCondition DcmSegmentation::writeFractionalFrames(Uint8* pixData, const Uint32 numFrames, const size_t pixDataLength)
 {
-  Uint32 numFrames = DcmIODUtil::limitMaxFrames(m_Frames.size(), "More than 2147483647 frames provided, will only write 2147483647");
-  OFCondition result;
-  Uint16 rows,cols;
-  rows = cols = 0;
-  getImagePixel().getRows(rows);
-  getImagePixel().getColumns(cols);
-  size_t numBytes = 0;
-  result = getTotalBytesRequired(rows, cols, numFrames, numBytes);
-  if (result.bad()) return result;
-  if (numBytes >= 4294967295UL)
-  {
-    DCMSEG_ERROR("Cannot store Segmentation objects with more than 4 GB pixel data (compression for writing not supported)");
-    return EC_TooManyBytesRequested;
-  }
-  Uint8* pixdata = new Uint8[numBytes];
-  OFVector<DcmIODTypes::Frame*>::iterator it = m_Frames.begin();
-  // Just copy bytes for each frame as is
-  for (size_t count = 0; it != m_Frames.end(); count++)
-  {
-    memcpy(pixdata + count*(*it)->length, (*it)->pixData, (*it)->length);
-    it++;
-  }
-  dataset.putAndInsertUint8Array(DCM_PixelData, pixdata, OFstatic_cast(unsigned long, numBytes), OFTrue);
-  delete[] pixdata;
-  return result;
+    OFVector<DcmIODTypes::Frame*>::iterator it = m_Frames.begin();
+    // Just copy bytes for each frame as is
+    for (size_t count = 0; it != m_Frames.end(); count++)
+    {
+        memcpy(pixData + count * (*it)->length, (*it)->pixData, (*it)->length);
+        it++;
+    }
+    return EC_Normal;
 }
 
-
-OFCondition DcmSegmentation::writeBinaryFrames(DcmItem& dataset)
+OFCondition DcmSegmentation::writeBinaryFrames(Uint8* pixData, Uint16 rows, Uint16 cols, const size_t pixDataLength)
 {
-  Uint16 rows, cols;
-  rows = cols = 0;
-  Uint32 numFrames = 0;
-  numFrames = DcmIODUtil::limitMaxFrames(m_Frames.size(), "More than 2147483647 frames provided, will only write 2147483647");
-  OFCondition result;
-  getImagePixel().getRows(rows);
-  getImagePixel().getColumns(cols);
-  size_t numBytes = 0;
-  result = getTotalBytesRequired(rows, cols, numFrames, numBytes);
-  if (result.bad()) return result;
-  if (numBytes >= 4294967295UL)
-  {
-    DCMSEG_ERROR("Cannot store Segmentation objects with more than 4 GB pixel data (compression for writing not supported)");
-    return EC_TooManyBytesRequested;
-  }
-  // Holds the pixels for all frames. Each bit represents a pixel which is either
-  // 1 (part of segment) or 0 (not part of segment. All frames are directly
-  // concatenated, i.e. there are no unused bits between the frames.
-  Uint8* pixdata = new Uint8[numBytes];
-  memset(pixdata, 0, numBytes);
-
-  // Fill Pixel Data Element
-  concatFrames(m_Frames, pixdata, rows*cols);
-  result = dataset.putAndInsertUint8Array(DCM_PixelData, pixdata, OFstatic_cast(unsigned long, numBytes), OFTrue);
-  delete [] pixdata;
-  return result;
-}
+    // Holds the pixels for all frames. Each bit represents a pixel which is either
+    // 1 (part of segment) or 0 (not part of segment. All frames are directly
+    // concatenated, i.e. there are no unused bits between the frames.
+    memset(pixData, 0, pixDataLength);
 
+    // Fill Pixel Data Element
+    concatFrames(m_Frames, pixData, rows * cols);
+    return EC_Normal;
+}
 
 OFCondition DcmSegmentation::writeSegmentationImageModule(DcmItem& dataset)
 {
-  dataset.putAndInsertOFStringArray(DCM_ImageType, "DERIVED\\PRIMARY");
-
-  OFCondition result = m_ContentIdentificationMacro.write(dataset);
-
-  /* Write hardcoded values */
-  if (result.good())
-  {
-    getImagePixel().setSamplesPerPixel(1);
-    getImagePixel().setPhotometricInterpretation("MONOCHROME2");
-    getImagePixel().setPixelRepresentation(0);
-
-    /* Write Bits Allocated/Stored, High Bit, Segmentation Fractional Type,
-     * Segmentation Type, Maximum Fractional Value
-     */
-    switch (m_SegmentationType)
-    {
-      case DcmSegTypes::ST_BINARY:
-      {
-        getImagePixel().setBitsAllocated(1);
-        getImagePixel().setBitsStored(1);
-        getImagePixel().setHighBit(0);
-        dataset.putAndInsertOFStringArray(DCM_SegmentationType, "BINARY");
-        break;
-      }
-      case DcmSegTypes::ST_FRACTIONAL:
-      {
-        getImagePixel().setBitsAllocated(8);
-        getImagePixel().setBitsStored(8);
-        getImagePixel().setHighBit(7);
-        dataset.putAndInsertOFStringArray(DCM_SegmentationType, "FRACTIONAL");
-        if (m_SegmentationFractionalType == DcmSegTypes::SFT_OCCUPANCY)
-        {
-          dataset.putAndInsertOFStringArray(DCM_SegmentationFractionalType, "OCCUPANCY");
-        }
-        else
+    dataset.putAndInsertOFStringArray(DCM_ImageType, "DERIVED\\PRIMARY");
+
+    OFCondition result = m_ContentIdentificationMacro.write(dataset);
+
+    /* Write hardcoded values */
+    if (result.good())
+    {
+        getImagePixel().setSamplesPerPixel(1);
+        getImagePixel().setPhotometricInterpretation("MONOCHROME2");
+        getImagePixel().setPixelRepresentation(0);
+
+        /* Write Bits Allocated/Stored, High Bit, Segmentation Fractional Type,
+         * Segmentation Type, Maximum Fractional Value
+         */
+        switch (m_SegmentationType)
         {
-          dataset.putAndInsertOFStringArray(DCM_SegmentationFractionalType, "PROBABILITY");
+            case DcmSegTypes::ST_BINARY:
+            {
+                getImagePixel().setBitsAllocated(1);
+                getImagePixel().setBitsStored(1);
+                getImagePixel().setHighBit(0);
+                dataset.putAndInsertOFStringArray(DCM_SegmentationType, "BINARY");
+                break;
+            }
+            case DcmSegTypes::ST_FRACTIONAL:
+            {
+                getImagePixel().setBitsAllocated(8);
+                getImagePixel().setBitsStored(8);
+                getImagePixel().setHighBit(7);
+                dataset.putAndInsertOFStringArray(DCM_SegmentationType, "FRACTIONAL");
+                if (m_SegmentationFractionalType == DcmSegTypes::SFT_OCCUPANCY)
+                {
+                    dataset.putAndInsertOFStringArray(DCM_SegmentationFractionalType, "OCCUPANCY");
+                }
+                else
+                {
+                    dataset.putAndInsertOFStringArray(DCM_SegmentationFractionalType, "PROBABILITY");
+                }
+                // Maximum Fractional Value: Attribute is type 1C but "required if .. FRACTIONAL", i.e. write type 1
+                DcmIODUtil::copyElementToDataset(
+                    result, dataset, m_MaximumFractionalValue, "1", "1", "SegmentationImageModule");
+                break;
+            }
+            case DcmSegTypes::ST_UNKNOWN:
+            {
+                DCMSEG_ERROR("Internal error, segmentation type not set");
+                result = EC_InternalError;
+                break;
+            }
         }
-        // Maximum Fractional Value: Attribute is type 1C but "required if .. FRACTIONAL", i.e. write type 1
-        DcmIODUtil::copyElementToDataset(result, dataset, m_MaximumFractionalValue, "1", "1", "SegmentationImageModule");
-        break;
-      }
-      case DcmSegTypes::ST_UNKNOWN:
-      {  DCMSEG_ERROR("Internal error, segmentation type not set");
-        result = EC_InternalError;
-        break;
-      }
-    }
-  }
-
-  /* Write segments */
-  OFVector<DcmItem*> segmentItems;
-  if (result.good())
-  {
-    OFVector<DcmSegment*>::iterator it = m_Segments.begin();
-    dataset.findAndDeleteElement(DCM_SegmentSequence);
-    for ( Uint16 itemCount = 0; (it != m_Segments.end()) && result.good(); itemCount++)
-    {
-      DcmItem* segmentItem = NULL;
-      dataset.findOrCreateSequenceItem(DCM_SegmentSequence, segmentItem, itemCount);
-      if (segmentItem)
-      {
-        result = (*it)->write(*segmentItem);
-        /* Insert segment number for the segment, starting from 1 and increasing monotonically. */
-        if (result.good())
+    }
+
+    /* Write segments */
+    OFVector<DcmItem*> segmentItems;
+    if (result.good())
+    {
+        OFVector<DcmSegment*>::iterator it = m_Segments.begin();
+        dataset.findAndDeleteElement(DCM_SegmentSequence);
+        for (Uint16 itemCount = 0; (it != m_Segments.end()) && result.good(); itemCount++)
         {
-          segmentItem->putAndInsertUint16(DCM_SegmentNumber, itemCount+1);
+            DcmItem* segmentItem = NULL;
+            dataset.findOrCreateSequenceItem(DCM_SegmentSequence, segmentItem, itemCount);
+            if (segmentItem)
+            {
+                result = (*it)->write(*segmentItem);
+                /* Insert segment number for the segment, starting from 1 and increasing monotonically. */
+                if (result.good())
+                {
+                    segmentItem->putAndInsertUint16(DCM_SegmentNumber, itemCount + 1);
+                }
+            }
+            else
+            {
+                DCMIOD_ERROR("Cannot create/get item in Segment Sequence (internal error)");
+                result = EC_InternalError;
+            }
+            it++;
         }
-      }
-      else
-      {
-        DCMIOD_ERROR("Cannot create/get item in Segment Sequence (internal error)");
-        result = EC_InternalError;
-      }
-      it++;
-    }
-  }
-
-  /* Write frame pixel data */
-  if (result.good())
-  {
-    if (m_SegmentationType == DcmSegTypes::ST_BINARY) result = writeBinaryFrames(dataset);
-    else if (m_SegmentationType == DcmSegTypes::ST_FRACTIONAL) result = writeFractionalFrames(dataset);
-    else result = SG_EC_UnknownSegmentationType;
-  }
-
-  return result;
+    }
+
+    return result;
 }
 
 // -- private helpers --
 
 void DcmSegmentation::clearData()
 {
-  DcmSegmentation::IODImage::clearData();
-  m_FG.clearData();
-  m_FGInterface.clear();
-  DcmIODUtil::freeContainer(m_Frames);
-  DcmIODUtil::freeContainer(m_Segments);
-  m_MaximumFractionalValue.clear();
-  m_SegmentationFractionalType = DcmSegTypes::SFT_UNKNOWN;
-  m_SegmentationType = DcmSegTypes::ST_UNKNOWN;
+    DcmSegmentation::IODImage::clearData();
+    m_FG.clearData();
+    m_FGInterface.clear();
+    DcmIODUtil::freeContainer(m_Frames);
+    DcmIODUtil::freeContainer(m_Segments);
+    m_MaximumFractionalValue.clear();
+    m_SegmentationFractionalType = DcmSegTypes::SFT_UNKNOWN;
+    m_SegmentationType           = DcmSegTypes::ST_UNKNOWN;
 }
 
-
 OFBool DcmSegmentation::checkPixDataLength(DcmElement* pixelData,
                                            const Uint16 rows,
                                            const Uint16 cols,
                                            const Uint16& numberOfFrames)
 {
-  // Get actual length of pixel data in bytes
-  size_t length = pixelData->getLengthField();
-
-  // Find out how many bytes are needed
-  size_t bytesRequired = 0;
-  OFCondition result = getTotalBytesRequired(rows, cols, numberOfFrames, bytesRequired);
-  if (result.bad()) return OFFalse;
-  // Length found in Pixel Data element is always even
-  if (bytesRequired % 2 == 1) bytesRequired++;
-  /* Compare expected and actual length */
-  if (length < bytesRequired)
-  {
-    DCMSEG_ERROR("Not enough bytes found in Pixel Data element. Found " << length << " bytes but " << bytesRequired << " bytes expected");
-    return OFFalse;
-  }
-  else if (length > bytesRequired)
-  {
-    DCMSEG_WARN("Too many bytes found in Pixel Data element. Found " << length << " bytes but " << bytesRequired << " bytes expected");
+    // Get actual length of pixel data in bytes
+    size_t length = pixelData->getLengthField();
+
+    // Find out how many bytes are needed
+    size_t bytesRequired = 0;
+    OFCondition result   = getTotalBytesRequired(rows, cols, numberOfFrames, bytesRequired);
+    if (result.bad())
+        return OFFalse;
+    // Length found in Pixel Data element is always even
+    if (bytesRequired % 2 == 1)
+        bytesRequired++;
+    /* Compare expected and actual length */
+    if (length < bytesRequired)
+    {
+        DCMSEG_ERROR("Not enough bytes found in Pixel Data element. Found " << length << " bytes but " << bytesRequired
+                                                                            << " bytes expected");
+        return OFFalse;
+    }
+    else if (length > bytesRequired)
+    {
+        DCMSEG_WARN("Too many bytes found in Pixel Data element. Found " << length << " bytes but " << bytesRequired
+                                                                         << " bytes expected");
+        return OFTrue;
+    }
+    else
+    {
+        DCMSEG_TRACE("Found " << length << " bytes in Pixel Data element as expected");
+    }
     return OFTrue;
-  }
-  else
-  {
-    DCMSEG_TRACE("Found " << length << " bytes in Pixel Data element as expected");
-  }
-  return OFTrue;
 }
 
-
 OFCondition DcmSegmentation::getTotalBytesRequired(const Uint16& rows,
                                                    const Uint16& cols,
                                                    const Uint32& numberOfFrames,
                                                    size_t& bytesRequired)
 {
-  OFBool ok = OFStandard::safeMult(OFstatic_cast(size_t, rows), OFstatic_cast(size_t, cols), bytesRequired);
-  if (ok) OFStandard::safeMult(bytesRequired, OFstatic_cast(size_t, numberOfFrames), bytesRequired);
-  if (!ok)
-  {
-    DCMSEG_ERROR("Cannot compute number of bytes required for Pixel Data since size_t type is too small");
-    return EC_TooManyBytesRequested;
-  }
-
-  /* for binary, we only need one bit per pixel */
-  size_t remainder = 0;
-  if (m_SegmentationType == DcmSegTypes::ST_BINARY)
-  {
-    // check whether the 1-bit pixels exactly fit into bytes
-    remainder = (OFstatic_cast(size_t, rows) * cols) % 8;
-    // number of bytes that work on an exact fit
-    bytesRequired = bytesRequired / 8;
-    // add one byte if we have a remainder
-    if (remainder > 0)
-    {
-      bytesRequired++;
-    }
-  }
-  return EC_Normal;
-}
+    OFBool ok = OFStandard::safeMult(OFstatic_cast(size_t, rows), OFstatic_cast(size_t, cols), bytesRequired);
+    if (ok)
+        OFStandard::safeMult(bytesRequired, OFstatic_cast(size_t, numberOfFrames), bytesRequired);
+    if (!ok)
+    {
+        DCMSEG_ERROR("Cannot compute number of bytes required for Pixel Data since size_t type is too small");
+        return EC_TooManyBytesRequested;
+    }
 
+    /* for binary, we only need one bit per pixel */
+    size_t remainder = 0;
+    if (m_SegmentationType == DcmSegTypes::ST_BINARY)
+    {
+        // check whether the 1-bit pixels exactly fit into bytes
+        remainder = (OFstatic_cast(size_t, rows) * cols) % 8;
+        // number of bytes that work on an exact fit
+        bytesRequired = bytesRequired / 8;
+        // add one byte if we have a remainder
+        if (remainder > 0)
+        {
+            bytesRequired++;
+        }
+    }
+    return EC_Normal;
+}
 
-OFCondition DcmSegmentation::loadFile(DcmFileFormat& dcmff,
-                                      const OFString& filename,
-                                      DcmDataset*& dset)
+OFCondition DcmSegmentation::loadFile(DcmFileFormat& dcmff, const OFString& filename, DcmDataset*& dset)
 {
-  dset = NULL;
-  OFCondition result = dcmff.loadFile(filename.c_str());
-  if (result.bad())
-  {
-    DCMSEG_ERROR("Could not load file " << filename << ": " << result.text());
+    dset               = NULL;
+    OFCondition result = dcmff.loadFile(filename.c_str());
+    if (result.bad())
+    {
+        DCMSEG_ERROR("Could not load file " << filename << ": " << result.text());
+        return result;
+    }
+    dset = dcmff.getDataset();
+    if (dset == NULL)
+    {
+        DCMSEG_ERROR("Could not load file " << filename << ": No dataset");
+        return IOD_EC_InvalidObject;
+    }
     return result;
-  }
-  dset = dcmff.getDataset();
-  if (dset == NULL)
-  {
-    DCMSEG_ERROR("Could not load file " << filename << ": No dataset");
-    return IOD_EC_InvalidObject;
-  }
-  return result;
 }
 
-
 OFCondition DcmSegmentation::readSegmentationFractionalType(DcmItem& item)
 {
-  m_SegmentationFractionalType = DcmSegTypes::SFT_UNKNOWN;
-  if (!item.tagExists(DCM_SegmentationFractionalType))
-  {
-    return EC_TagNotFound;
-  }
-  DcmCodeString element(DCM_SegmentationFractionalType);
-  OFCondition result = DcmIODUtil::getAndCheckElementFromDataset(item, element, getRules()->getByTag(DCM_SegmentationFractionalType));
-  OFString str;
-  if (result.good())
-  {
-    element.getOFStringArray(str);
-    m_SegmentationFractionalType = DcmSegTypes::OFString2FractionalType(str);
-  }
-
-  if (m_SegmentationFractionalType  == DcmSegTypes::SFT_UNKNOWN)
-  {
-    DCMSEG_ERROR("Invalid value for attribute Segmentation Fractional Type: " << str);
-    return EC_InvalidValue;
-  }
-  else
-    return EC_Normal;
-}
+    m_SegmentationFractionalType = DcmSegTypes::SFT_UNKNOWN;
+    if (!item.tagExists(DCM_SegmentationFractionalType))
+    {
+        return EC_TagNotFound;
+    }
+    DcmCodeString element(DCM_SegmentationFractionalType);
+    OFCondition result = DcmIODUtil::getAndCheckElementFromDataset(
+        item, element, getRules()->getByTag(DCM_SegmentationFractionalType));
+    OFString str;
+    if (result.good())
+    {
+        element.getOFStringArray(str);
+        m_SegmentationFractionalType = DcmSegTypes::OFString2FractionalType(str);
+    }
 
+    if (m_SegmentationFractionalType == DcmSegTypes::SFT_UNKNOWN)
+    {
+        DCMSEG_ERROR("Invalid value for attribute Segmentation Fractional Type: " << str);
+        return EC_InvalidValue;
+    }
+    else
+        return EC_Normal;
+}
 
 OFCondition DcmSegmentation::readSegmentationType(DcmItem& item)
 {
-  m_SegmentationType = DcmSegTypes::ST_UNKNOWN;
-  if (!item.tagExists(DCM_SegmentationType))
-  {
-    return EC_TagNotFound;
-  }
-
-  DcmCodeString element(DCM_SegmentationType);
-  OFCondition result = DcmIODUtil::getAndCheckElementFromDataset(item, element, getRules()->getByTag(DCM_SegmentationType));
-  OFString str;
-  if (result.good())
-  {
-    element.getOFStringArray(str);
-    m_SegmentationType = DcmSegTypes::OFString2Segtype(str);
-  }
-
-  if (m_SegmentationType == DcmSegTypes::ST_UNKNOWN)
-  {
-    DCMSEG_ERROR("Invalid value for attribute Segmentation Type: " << str);
-    result = EC_InvalidValue;
-  }
-
-  return result;
-}
+    m_SegmentationType = DcmSegTypes::ST_UNKNOWN;
+    if (!item.tagExists(DCM_SegmentationType))
+    {
+        return EC_TagNotFound;
+    }
 
+    DcmCodeString element(DCM_SegmentationType);
+    OFCondition result
+        = DcmIODUtil::getAndCheckElementFromDataset(item, element, getRules()->getByTag(DCM_SegmentationType));
+    OFString str;
+    if (result.good())
+    {
+        element.getOFStringArray(str);
+        m_SegmentationType = DcmSegTypes::OFString2Segtype(str);
+    }
+
+    if (m_SegmentationType == DcmSegTypes::ST_UNKNOWN)
+    {
+        DCMSEG_ERROR("Invalid value for attribute Segmentation Type: " << str);
+        result = EC_InvalidValue;
+    }
+
+    return result;
+}
 
 // protected override of public base class function
 IODImagePixelModule<Uint8>& DcmSegmentation::getImagePixel()
 {
-  return *OFget<IODImagePixelModule<Uint8> >( &DcmSegmentation::IODImage::getImagePixel() );
+    return *OFget<IODImagePixelModule<Uint8> >(&DcmSegmentation::IODImage::getImagePixel());
 }
 
-
 OFBool DcmSegmentation::check(const OFBool checkFGStructure)
 {
-  if (m_Frames.size() == 0)
-  {
-    DCMSEG_ERROR("No frame data available");
-    return OFFalse;
-  }
-  if (m_Segments.size() == 0)
-  {
-    DCMSEG_ERROR("No segments defined");
-    return OFFalse;
-  }
-  if (m_Segments.size() > m_Frames.size())
-  {
-    DCMSEG_ERROR("There are more segments than frames defined");
-    return OFFalse;
-  }
-
-  if (checkFGStructure)
-  {
-     if (!m_FGInterface.check())
-       return OFFalse;
-  }
-
-  // Check rules around Frame of Reference
-
-  // 1. If Derivation Image FG is not present, Frame of Reference is required.
-  OFBool frameOfRefRequired = OFFalse;
-  FGBase* group = m_FGInterface.get(OFstatic_cast(Uint32, 0), DcmFGTypes::EFG_DERIVATIONIMAGE);
-  if (group == NULL)
-  {
-    // Derivation Image FG is not present, FoR is required
-    frameOfRefRequired = OFTrue;
-  }
-  else
-  {
-    // Derivation Image FG present, Frame of Reference is not required
-    frameOfRefRequired = OFFalse;
-  }
-  OFString frameOfRef;
-  getFrameOfReference().getFrameOfReferenceUID(frameOfRef);
-  if (frameOfRefRequired && frameOfRef.empty())
-  {
-    DCMSEG_ERROR("Frame of Reference UID is not set for Segmentation but is required");
-    return OFFalse;
-  }
-
-  // 2. When a Frame of Reference UID is present the segment shall be specified
-  // within that coordinate system, using the Pixel Measures, Plane Position
-  // (Patient) and Plane Orientation (Patient) Functional Groups.
-  if (!frameOfRef.empty())
-  {
-    // Check that each of above FGs is present. We do not check this for
-    // all frames since if it exists for one frame it must exist for all others.
-    // This is a general rule and applies for all FGs, so it is not checked here.
-    group = m_FGInterface.get(OFstatic_cast(Uint32, 0), DcmFGTypes::EFG_PIXELMEASURES);
-    if (!group)
-    {
-      DCMSEG_ERROR("Frame of Reference UID is present but Pixel Measures FG is missing");
-      return OFFalse;
-    }
-    group = m_FGInterface.get(OFstatic_cast(Uint32, 0), DcmFGTypes::EFG_PLANEPOSPATIENT);
-    if (!group)
-    {
-      DCMSEG_ERROR("Frame of Reference UID is present but Plane Position (Patient) FG is missing");
-      return OFFalse;
-    }
-    group = m_FGInterface.get(OFstatic_cast(Uint32, 0), DcmFGTypes::EFG_PLANEORIENTPATIENT);
-    if (!group)
-    {
-      DCMSEG_ERROR("Frame of Reference UID is present but Plane Orientation (Patient) FG is missing");
-      return OFFalse;
-    }
-  }
-  // Another condition cannot be checked since we do not have access to the
-  // datasets of the source images:
-  // 3. If FoR is present but not the same in images this segmentation applies to,
-  // (those in Derivation Image FG), each pixel of the segmentation shall
-  // correspond to a pixel in a referenced image (i.e. they must share the same
-  // size and resolution).
-
-  return OFTrue;
-}
+    if (m_Frames.size() == 0)
+    {
+        DCMSEG_ERROR("No frame data available");
+        return OFFalse;
+    }
+    if (m_Segments.size() == 0)
+    {
+        DCMSEG_ERROR("No segments defined");
+        return OFFalse;
+    }
+    if (m_Segments.size() > m_Frames.size())
+    {
+        DCMSEG_ERROR("There are more segments than frames defined");
+        return OFFalse;
+    }
 
+    if (checkFGStructure)
+    {
+        if (!m_FGInterface.check())
+            return OFFalse;
+    }
 
-OFCondition DcmSegmentation::decompress(DcmDataset& dset)
-{
-  DcmXfer xfer = dset.getOriginalXfer();
-  OFCondition result;
-  // If the original transfer syntax could have been lossy, print warning
-  if (dset.hasRepresentation(EXS_LittleEndianExplicit, NULL))
-  {
-    if ( xfer.isEncapsulated() && (xfer.getXfer() != EXS_RLELossless) && (xfer.getXfer() != EXS_DeflatedLittleEndianExplicit) )
+    // Check rules around Frame of Reference
+
+    // 1. If Derivation Image FG is not present, Frame of Reference is required.
+    OFBool frameOfRefRequired = OFFalse;
+    FGBase* group             = m_FGInterface.get(OFstatic_cast(Uint32, 0), DcmFGTypes::EFG_DERIVATIONIMAGE);
+    if (group == NULL)
     {
-      DCMSEG_WARN("Dataset has been compressed using a (possibly) lossy compression scheme (ignored)");
+        // Derivation Image FG is not present, FoR is required
+        frameOfRefRequired = OFTrue;
     }
-  }
-  // If the original transfer is encapsulated and we do not already have an uncompressed version, decompress or reject the file
-  else if (xfer.isEncapsulated())
-  {
-    // RLE compression is fine (truly lossless). Deflated is handled internally by DCMTK.
-    if (xfer.getXfer() == EXS_RLELossless)
+    else
     {
-      DCMSEG_DEBUG("DICOM file is RLE-compressed, converting to uncompressed transfer syntax first");
-      result = DcmIODUtil::decompress(dset);
+        // Derivation Image FG present, Frame of Reference is not required
+        frameOfRefRequired = OFFalse;
     }
-    else // We do not accept any transfer syntax that could be lossy compressed
+    OFString frameOfRef;
+    getFrameOfReference().getFrameOfReferenceUID(frameOfRef);
+    if (frameOfRefRequired && frameOfRef.empty())
     {
-      DCMSEG_ERROR("Transfer syntax " << DcmXfer(xfer).getXferName() << " uses lossy compression, not supported for Segmentation objects!");
-      result = IOD_EC_CannotDecompress;
+        DCMSEG_ERROR("Frame of Reference UID is not set for Segmentation but is required");
+        return OFFalse;
     }
-  }
-  return result;
-}
 
+    // 2. When a Frame of Reference UID is present the segment shall be specified
+    // within that coordinate system, using the Pixel Measures, Plane Position
+    // (Patient) and Plane Orientation (Patient) Functional Groups.
+    if (!frameOfRef.empty())
+    {
+        // Check that each of above FGs is present. We do not check this for
+        // all frames since if it exists for one frame it must exist for all others.
+        // This is a general rule and applies for all FGs, so it is not checked here.
+        group = m_FGInterface.get(OFstatic_cast(Uint32, 0), DcmFGTypes::EFG_PIXELMEASURES);
+        if (!group)
+        {
+            DCMSEG_ERROR("Frame of Reference UID is present but Pixel Measures FG is missing");
+            return OFFalse;
+        }
+        group = m_FGInterface.get(OFstatic_cast(Uint32, 0), DcmFGTypes::EFG_PLANEPOSPATIENT);
+        if (!group)
+        {
+            DCMSEG_ERROR("Frame of Reference UID is present but Plane Position (Patient) FG is missing");
+            return OFFalse;
+        }
+        group = m_FGInterface.get(OFstatic_cast(Uint32, 0), DcmFGTypes::EFG_PLANEORIENTPATIENT);
+        if (!group)
+        {
+            DCMSEG_ERROR("Frame of Reference UID is present but Plane Orientation (Patient) FG is missing");
+            return OFFalse;
+        }
+    }
+    // Another condition cannot be checked since we do not have access to the
+    // datasets of the source images:
+    // 3. If FoR is present but not the same in images this segmentation applies to,
+    // (those in Derivation Image FG), each pixel of the segmentation shall
+    // correspond to a pixel in a referenced image (i.e. they must share the same
+    // size and resolution).
+
+    return OFTrue;
+}
 
-OFCondition DcmSegmentation::extractFrames(Uint8* pixData,
-                                           const size_t numFrames,
-                                           const size_t bitsPerFrame,
-                                           OFVector< DcmIODTypes::Frame* >& results)
+OFCondition DcmSegmentation::decompress(DcmDataset& dset)
 {
-  // Will hold the bit position (0-7) that the current frame starts from. The
-  // first frame will always start at bit 0.
-  Uint8  bitShift = 0;
-  // Compute length in bytes we need to consider for each frame.
-  size_t frameLengthBytes = bitsPerFrame / 8;
-  // If the number of bits is not dividable by 8, we need part of an extra
-  // byte in the end. Since we like to set the unused bits to 0 in such a last
-  // byte to 0, remember the number.
-  size_t overlapBits = (8 - (bitsPerFrame % 8)) % 8;
-  // Add an extra byte if we we fill a partial byte in the end
-  if (overlapBits != 0) frameLengthBytes++;
-  // Points to current reading position within pixData
-  Uint8* readPos = pixData;
-  // Loop over each frame and copy it to Frame structures
-  for (size_t f = 0; f < numFrames; f++)
-  {
-    // Create frame with correct length and copy 1:1 from pixel data
-    DcmIODTypes::Frame* frame = new DcmIODTypes::Frame();
-    frame->length = frameLengthBytes;
-    frame->pixData = new Uint8[frameLengthBytes];
-    if (!frame->pixData)
+    DcmXfer xfer = dset.getOriginalXfer();
+    OFCondition result;
+    // If the original transfer syntax could have been lossy, print warning
+    if (dset.hasRepresentation(EXS_LittleEndianExplicit, NULL))
     {
-        return EC_MemoryExhausted;
-    }
-    memcpy(frame->pixData, readPos, frame->length);
-    // If we have been copying too much, i.e the first bits of the frame
-    // actually belong to the former frame, shift the whole frame this amount
-    // of bits to the left in order to shift the superfluous bits out, i.e.
-    // make frame start at byte boundary.
-    if (bitShift > 0)
-    {
-      DcmSegUtils::alignFrameOnByteBoundary(frame->pixData, frame->length, 8-bitShift);
-    }
-    // Adapt last byte by masking out unused bits (i.e. those belonging to next frame).
-    // A reader should ignore those unused bits anyway.
-    frame->pixData[frame->length-1] = (frame->pixData[frame->length-1] << (overlapBits)) >> (overlapBits);
-    // Store frame
-    results.push_back(frame);
-    // Compute the bitshift created by this frame
-    bitShift = ( 8- ((f+1) * bitsPerFrame) % 8 ) % 8;
-    // If the previous byte read has not been used completely, i.e. it contains
-    // also bytes of the next frame, rewind read position to the previous byte
-    // that was partially read. Otherwise skip to the next full byte.
-    if (bitShift > 0)
-    {
-      readPos = readPos + frame->length - 1;
+        if (xfer.isEncapsulated() && (xfer.getXfer() != EXS_RLELossless)
+            && (xfer.getXfer() != EXS_DeflatedLittleEndianExplicit))
+        {
+            DCMSEG_WARN("Dataset has been compressed using a (possibly) lossy compression scheme (ignored)");
+        }
     }
-    else
+    // If the original transfer is encapsulated and we do not already have an uncompressed version, decompress or reject
+    // the file
+    else if (xfer.isEncapsulated())
     {
-      readPos = readPos + frame->length;
+        // RLE compression is fine (truly lossless). Deflated is handled internally by DCMTK.
+        if (xfer.getXfer() == EXS_RLELossless)
+        {
+            DCMSEG_DEBUG("DICOM file is RLE-compressed, converting to uncompressed transfer syntax first");
+            result = DcmIODUtil::decompress(dset);
+        }
+        else // We do not accept any transfer syntax that could be lossy compressed
+        {
+            DCMSEG_ERROR("Transfer syntax " << DcmXfer(xfer).getXferName()
+                                            << " uses lossy compression, not supported for Segmentation objects!");
+            result = IOD_EC_CannotDecompress;
+        }
     }
-  }
-  return EC_Normal;
+    return result;
 }
 
-
-void DcmSegmentation::concatFrames(OFVector< DcmIODTypes::Frame* > frames,
-                                   Uint8* pixData,
-                                   const size_t bitsPerFrame)
+void DcmSegmentation::concatFrames(OFVector<DcmIODTypes::Frame*> frames, Uint8* pixData, const size_t bitsPerFrame)
 {
-  // Writing position within the pixData memory
-  Uint8 *writePos = pixData;
-  OFVector<DcmIODTypes::Frame*>::iterator frame = frames.begin();
-  Uint8 freeBits = 0;
-  Uint8 firstByte = 0;
-  // Iterate over frames and copy each to pixData memory
-  for (size_t f = 0; frame != frames.end(); f++)
-  {
-    DCMSEG_DEBUG("Packing segmentation frame #" << f+1 << "/" << frames.size());
-    // Backup first byte of the destination since it may contain bits of the
-    // previous frame; mask out those bits not belonging to previous frame.
-    // This will potentially create some empty bits on the left of the byte,
-    // that the current frame can use to store the its own first bits.
-    firstByte = (writePos[0] << freeBits) >> freeBits;
-    memcpy(writePos, (*frame)->pixData, (*frame)->length);
-    // If the previous frame left over some unused bits, shift the current frame
-    // that number of bits to the left, and restore the original bits of the
-    // previous frame that are overwritten by the shifting operation.
-    if (freeBits > 0)
+    // Writing position within the pixData memory
+    Uint8* writePos                               = pixData;
+    OFVector<DcmIODTypes::Frame*>::iterator frame = frames.begin();
+    Uint8 freeBits                                = 0;
+    Uint8 firstByte                               = 0;
+    // Iterate over frames and copy each to pixData memory
+    for (size_t f = 0; frame != frames.end(); f++)
     {
-      DcmSegUtils::alignFrameOnBitPosition(writePos, (*frame)->length, 8-freeBits);
-      writePos[0] |= firstByte;
+        DCMSEG_DEBUG("Packing segmentation frame #" << f + 1 << "/" << frames.size());
+        // Backup first byte of the destination since it may contain bits of the
+        // previous frame; mask out those bits not belonging to previous frame.
+        // This will potentially create some empty bits on the left of the byte,
+        // that the current frame can use to store the its own first bits.
+        firstByte = (writePos[0] << freeBits) >> freeBits;
+        memcpy(writePos, (*frame)->pixData, (*frame)->length);
+        // If the previous frame left over some unused bits, shift the current frame
+        // that number of bits to the left, and restore the original bits of the
+        // previous frame that are overwritten by the shifting operation.
+        if (freeBits > 0)
+        {
+            DcmSegUtils::alignFrameOnBitPosition(writePos, (*frame)->length, 8 - freeBits);
+            writePos[0] |= firstByte;
+        }
+        // Compute free bits left over from this frame in the previous byte written
+        freeBits = (8 - (((f + 1) * bitsPerFrame) % 8)) % 8;
+        // If we have free bits, the previous byte written to will be the first byte
+        // we write to for the next frame. Otherwise start with a fresh destination
+        // byte.
+        if (freeBits > 0)
+        {
+            writePos = writePos + (*frame)->length - 1;
+        }
+        else
+        {
+            writePos = writePos + (*frame)->length;
+        }
+        // Next frame
+        frame++;
     }
-    // Compute free bits left over from this frame in the previous byte written
-    freeBits = (8 - (( (f+1) * bitsPerFrame ) % 8)) % 8;
-    // If we have free bits, the previous byte written to will be the first byte
-    // we write to for the next frame. Otherwise start with a fresh destination
-    // byte.
+    // Through shifting we can have non-zero bits within the unused bits of the
+    // last byte. Fill them with zeros (though not required by the standard).
     if (freeBits > 0)
     {
-      writePos = writePos + (*frame)->length - 1;
+        *writePos = (*writePos >> freeBits) << freeBits;
     }
-    else
-    {
-      writePos = writePos + (*frame)->length;
-    }
-    // Next frame
-    frame++;
-  }
-  // Through shifting we can have non-zero bits within the unused bits of the
-  // last byte. Fill them with zeros (though not required by the standard).
-  if (freeBits > 0)
-  {
-    *writePos = (*writePos >> freeBits) << freeBits;
-  }
 }
index de0ef59f4f1c44b4021daafe4b9f4c2d9ffe4dae..8db7b5fc6b8116593dea709df960e1659f235464 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2017, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  *  Purpose: Class representing a Segment from the Segment Ident. Sequence
  *
  */
+
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmiod/iodutil.h"
+#include "dcmtk/dcmseg/segdoc.h"
 #include "dcmtk/dcmseg/segment.h"
 #include "dcmtk/dcmseg/segtypes.h"
-#include "dcmtk/dcmseg/segdoc.h"
-
 
 OFCondition DcmSegment::create(DcmSegment*& segment,
                                const OFString& segmentLabel,
@@ -33,364 +34,320 @@ OFCondition DcmSegment::create(DcmSegment*& segment,
                                const OFString& algoName)
 
 {
-  segment = new DcmSegment();
-  if (segment == NULL)
-    return EC_MemoryExhausted;
+    segment = new DcmSegment();
+    if (segment == NULL)
+        return EC_MemoryExhausted;
 
-  OFCondition result = segment->setSegmentLabel(segmentLabel, OFTrue /* check value */);
+    OFCondition result = segment->setSegmentLabel(segmentLabel, OFTrue /* check value */);
 
-  if (result.good())
-  {
-    segment->m_SegmentDescription.getSegmentedPropertyCategoryCode() = segmentedPropertyCategory;
-    result = segment->m_SegmentDescription.getSegmentedPropertyCategoryCode().check();
-  }
-
-  if (result.good())
-  {
-    segment->m_SegmentDescription.getSegmentedPropertyTypeCode() = segmentedPropertyType;
-    result = segment->getSegmentedPropertyTypeCode().check();
-  }
+    if (result.good())
+    {
+        segment->m_SegmentDescription.getSegmentedPropertyCategoryCode() = segmentedPropertyCategory;
+        result = segment->m_SegmentDescription.getSegmentedPropertyCategoryCode().check();
+    }
 
+    if (result.good())
+    {
+        segment->m_SegmentDescription.getSegmentedPropertyTypeCode() = segmentedPropertyType;
+        result                                                       = segment->getSegmentedPropertyTypeCode().check();
+    }
 
-  if (result.good())
-  {
-      result = segment->setSegmentAlgorithm(algoType, algoName, OFTrue);
-  }
+    if (result.good())
+    {
+        result = segment->setSegmentAlgorithm(algoType, algoName, OFTrue);
+    }
 
-  if ( result.bad() )
-  {
-    delete segment;
-    segment = NULL;
-  }
+    if (result.bad())
+    {
+        delete segment;
+        segment = NULL;
+    }
 
-  return result;
+    return result;
 }
 
-
-
-OFCondition DcmSegment::read(DcmItem& item,
-                             const OFBool clearOldData)
+OFCondition DcmSegment::read(DcmItem& item, const OFBool clearOldData)
 {
-  if (clearOldData)
-    clearData();
-
-  m_SegmentDescription.read(item);
-  DcmIODUtil::getAndCheckElementFromDataset(item, m_SegmentAlgorithmName, m_Rules.getByTag(DCM_SegmentAlgorithmName));
-
-  DcmIODUtil::readSingleItem<AlgorithmIdentificationMacro>(
-    item,
-    DCM_SegmentationAlgorithmIdentificationSequence,
-    m_SegmentationAlgorithmIdentification,
-    "3",
-    "Segmentation Image Module");
-
-  DcmIODUtil::getAndCheckElementFromDataset(item, m_RecommendedDisplayGrayscaleValue, m_Rules.getByTag(DCM_RecommendedDisplayGrayscaleValue));
-  DcmIODUtil::getAndCheckElementFromDataset(item, m_RecommendedDisplayCIELabValue, m_Rules.getByTag(DCM_RecommendedDisplayCIELabValue));
-  DcmIODUtil::getAndCheckElementFromDataset(item, m_TrackingID, m_Rules.getByTag(DCM_TrackingID));
-  DcmIODUtil::getAndCheckElementFromDataset(item, m_TrackingUID, m_Rules.getByTag(DCM_TrackingUID));
-
-  return EC_Normal;
+    if (clearOldData)
+        clearData();
+
+    m_SegmentDescription.read(item);
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_SegmentAlgorithmName, m_Rules.getByTag(DCM_SegmentAlgorithmName));
+
+    DcmIODUtil::readSingleItem<AlgorithmIdentificationMacro>(item,
+                                                             DCM_SegmentationAlgorithmIdentificationSequence,
+                                                             m_SegmentationAlgorithmIdentification,
+                                                             "3",
+                                                             "Segmentation Image Module");
+
+    DcmIODUtil::getAndCheckElementFromDataset(
+        item, m_RecommendedDisplayGrayscaleValue, m_Rules.getByTag(DCM_RecommendedDisplayGrayscaleValue));
+    DcmIODUtil::getAndCheckElementFromDataset(
+        item, m_RecommendedDisplayCIELabValue, m_Rules.getByTag(DCM_RecommendedDisplayCIELabValue));
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_TrackingID, m_Rules.getByTag(DCM_TrackingID));
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_TrackingUID, m_Rules.getByTag(DCM_TrackingUID));
+
+    return EC_Normal;
 }
 
-
 OFCondition DcmSegment::write(DcmItem& item)
 {
-  OFCondition result;
-  result = m_SegmentDescription.write(item);
-  DcmIODUtil::copyElementToDataset(result, item, m_SegmentAlgorithmName, m_Rules.getByTag(DCM_SegmentAlgorithmName));
-
-  if (result.good() && m_SegmentationAlgorithmIdentification.check(OFTrue /* quiet */).good())
-  {
-    DcmIODUtil::writeSingleItem<AlgorithmIdentificationMacro>(
-    result,
-    DCM_SegmentationAlgorithmIdentificationSequence,
-    m_SegmentationAlgorithmIdentification,
-    item,
-    "3",
-    "Segmentation Image Module");
-  }
-
-  DcmIODUtil::copyElementToDataset(result, item, m_RecommendedDisplayGrayscaleValue, m_Rules.getByTag(DCM_RecommendedDisplayGrayscaleValue));
-  DcmIODUtil::copyElementToDataset(result, item, m_RecommendedDisplayCIELabValue, m_Rules.getByTag(DCM_RecommendedDisplayCIELabValue));
-  DcmIODUtil::copyElementToDataset(result, item, m_TrackingID, m_Rules.getByTag(DCM_TrackingID));
-  DcmIODUtil::copyElementToDataset(result, item, m_TrackingUID, m_Rules.getByTag(DCM_TrackingUID));
-
-  return result;
-}
+    OFCondition result;
+    result = m_SegmentDescription.write(item);
+    DcmIODUtil::copyElementToDataset(result, item, m_SegmentAlgorithmName, m_Rules.getByTag(DCM_SegmentAlgorithmName));
 
+    if (result.good() && m_SegmentationAlgorithmIdentification.check(OFTrue /* quiet */).good())
+    {
+        DcmIODUtil::writeSingleItem<AlgorithmIdentificationMacro>(result,
+                                                                  DCM_SegmentationAlgorithmIdentificationSequence,
+                                                                  m_SegmentationAlgorithmIdentification,
+                                                                  item,
+                                                                  "3",
+                                                                  "Segmentation Image Module");
+    }
 
+    DcmIODUtil::copyElementToDataset(
+        result, item, m_RecommendedDisplayGrayscaleValue, m_Rules.getByTag(DCM_RecommendedDisplayGrayscaleValue));
+    DcmIODUtil::copyElementToDataset(
+        result, item, m_RecommendedDisplayCIELabValue, m_Rules.getByTag(DCM_RecommendedDisplayCIELabValue));
+    DcmIODUtil::copyElementToDataset(result, item, m_TrackingID, m_Rules.getByTag(DCM_TrackingID));
+    DcmIODUtil::copyElementToDataset(result, item, m_TrackingUID, m_Rules.getByTag(DCM_TrackingUID));
+
+    return result;
+}
 
 void DcmSegment::clearData()
 {
-  m_SegmentDescription.clearData();
-  m_SegmentAlgorithmName.clear();
-  m_SegmentationAlgorithmIdentification.clearData();
-  m_RecommendedDisplayGrayscaleValue.clear();
-  m_RecommendedDisplayCIELabValue.clear();
-  m_TrackingID.clear();
-  m_TrackingUID.clear();
+    m_SegmentDescription.clearData();
+    m_SegmentAlgorithmName.clear();
+    m_SegmentationAlgorithmIdentification.clearData();
+    m_RecommendedDisplayGrayscaleValue.clear();
+    m_RecommendedDisplayCIELabValue.clear();
+    m_TrackingID.clear();
+    m_TrackingUID.clear();
 }
 
-
-
 DcmSegment::~DcmSegment()
 {
-  clearData();
+    clearData();
 }
 
-
 // protected default constructor
-DcmSegment::DcmSegment() :
-  m_SegmentationDoc(NULL),
-  m_SegmentDescription(),
-  m_SegmentAlgorithmName(DCM_SegmentAlgorithmName),
-  m_SegmentationAlgorithmIdentification(),
-  m_RecommendedDisplayGrayscaleValue(DCM_RecommendedDisplayGrayscaleValue),
-  m_RecommendedDisplayCIELabValue(DCM_RecommendedDisplayCIELabValue),
-  m_TrackingID(DCM_TrackingID),
-  m_TrackingUID(DCM_TrackingUID),
-  m_Rules()
+DcmSegment::DcmSegment()
+    : m_SegmentationDoc(NULL)
+    , m_SegmentDescription()
+    , m_SegmentAlgorithmName(DCM_SegmentAlgorithmName)
+    , m_SegmentationAlgorithmIdentification()
+    , m_RecommendedDisplayGrayscaleValue(DCM_RecommendedDisplayGrayscaleValue)
+    , m_RecommendedDisplayCIELabValue(DCM_RecommendedDisplayCIELabValue)
+    , m_TrackingID(DCM_TrackingID)
+    , m_TrackingUID(DCM_TrackingUID)
+    , m_Rules()
 {
-  initIODRules();
+    initIODRules();
 }
 
-
 void DcmSegment::initIODRules()
 {
-  m_Rules.addRule(new IODRule(DCM_SegmentAlgorithmName, "1","1C","SegmentationImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules.addRule(new IODRule(DCM_RecommendedDisplayGrayscaleValue, "1","3","SegmentationImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules.addRule(new IODRule(DCM_RecommendedDisplayCIELabValue, "3","3","SegmentationImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules.addRule(new IODRule(DCM_TrackingID, "1","1C","SegmentationImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
-  m_Rules.addRule(new IODRule(DCM_TrackingUID, "1","1C","SegmentationImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules.addRule(new IODRule(DCM_SegmentAlgorithmName, "1", "1C", "SegmentationImageModule", DcmIODTypes::IE_IMAGE),
+                    OFTrue);
+    m_Rules.addRule(
+        new IODRule(DCM_RecommendedDisplayGrayscaleValue, "1", "3", "SegmentationImageModule", DcmIODTypes::IE_IMAGE),
+        OFTrue);
+    m_Rules.addRule(
+        new IODRule(DCM_RecommendedDisplayCIELabValue, "3", "3", "SegmentationImageModule", DcmIODTypes::IE_IMAGE),
+        OFTrue);
+    m_Rules.addRule(new IODRule(DCM_TrackingID, "1", "1C", "SegmentationImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
+    m_Rules.addRule(new IODRule(DCM_TrackingUID, "1", "1C", "SegmentationImageModule", DcmIODTypes::IE_IMAGE), OFTrue);
 }
 
-
 // -------------- getters --------------------
 
 unsigned int DcmSegment::getSegmentNumber()
 {
-  unsigned int value = 0;
-  if (m_SegmentationDoc != NULL)
-  {
-    m_SegmentationDoc->getSegmentNumber(this, value);
-  }
-  return value;
+    unsigned int value = 0;
+    if (m_SegmentationDoc != NULL)
+    {
+        m_SegmentationDoc->getSegmentNumber(this, value);
+    }
+    return value;
 }
 
-
-OFCondition DcmSegment::getSegmentLabel(OFString& value,
-                                        const signed long pos)
+OFCondition DcmSegment::getSegmentLabel(OFString& value, const signed long pos)
 {
-  return m_SegmentDescription.getSegmentLabel(value, pos);
+    return m_SegmentDescription.getSegmentLabel(value, pos);
 }
 
-
-OFCondition DcmSegment::getSegmentDescription(OFString& value,
-                                              const signed long pos)
+OFCondition DcmSegment::getSegmentDescription(OFString& value, const signed long pos)
 {
-  return m_SegmentDescription.getSegmentDescription(value, pos);
+    return m_SegmentDescription.getSegmentDescription(value, pos);
 }
 
-
 DcmSegTypes::E_SegmentAlgoType DcmSegment::getSegmentAlgorithmType()
 {
-  return m_SegmentDescription.getSegmentAlgorithmType();
+    return m_SegmentDescription.getSegmentAlgorithmType();
 }
 
-OFCondition DcmSegment::getSegmentAlgorithmName(OFString& value,
-                                                const signed long pos)
+OFCondition DcmSegment::getSegmentAlgorithmName(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_SegmentAlgorithmName, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_SegmentAlgorithmName, value, pos);
 }
 
-
 GeneralAnatomyMacro& DcmSegment::getGeneralAnatomyCode()
 {
-  return m_SegmentDescription.getGeneralAnatomyCode();
+    return m_SegmentDescription.getGeneralAnatomyCode();
 }
 
-
 AlgorithmIdentificationMacro& DcmSegment::getSegmentationAlgorithmIdentification()
 {
-  return m_SegmentationAlgorithmIdentification;
+    return m_SegmentationAlgorithmIdentification;
 }
 
-
 CodeSequenceMacro& DcmSegment::getSegmentedPropertyCategoryCode()
 {
-  return m_SegmentDescription.getSegmentedPropertyCategoryCode();
+    return m_SegmentDescription.getSegmentedPropertyCategoryCode();
 }
 
-
 CodeSequenceMacro& DcmSegment::getSegmentedPropertyTypeCode()
 {
-  return m_SegmentDescription.getSegmentedPropertyTypeCode();
+    return m_SegmentDescription.getSegmentedPropertyTypeCode();
 }
 
-
-OFVector< CodeSequenceMacro* >& DcmSegment::getSegmentedPropertyTypeModifierCode()
+OFVector<CodeSequenceMacro*>& DcmSegment::getSegmentedPropertyTypeModifierCode()
 {
-  return m_SegmentDescription.getSegmentedPropertyTypeModifier();
+    return m_SegmentDescription.getSegmentedPropertyTypeModifier();
 }
 
-
-
-OFCondition DcmSegment::getRecommendedDisplayGrayscaleValue(Uint16& value,
-                                                            const unsigned long pos)
+OFCondition DcmSegment::getRecommendedDisplayGrayscaleValue(Uint16& value, const unsigned long pos)
 {
-  return m_RecommendedDisplayGrayscaleValue.getUint16(value, pos);
+    return m_RecommendedDisplayGrayscaleValue.getUint16(value, pos);
 }
 
-
-OFCondition DcmSegment::getRecommendedDisplayCIELabValue(Uint16& L,
-                                                         Uint16& a,
-                                                         Uint16& b)
+OFCondition DcmSegment::getRecommendedDisplayCIELabValue(Uint16& L, Uint16& a, Uint16& b)
 {
-  OFCondition result = m_RecommendedDisplayCIELabValue.getUint16(L, 0);
-  if (result.good())
-    result = m_RecommendedDisplayCIELabValue.getUint16(a, 1);
+    OFCondition result = m_RecommendedDisplayCIELabValue.getUint16(L, 0);
+    if (result.good())
+        result = m_RecommendedDisplayCIELabValue.getUint16(a, 1);
 
-  if (result.good())
-    result = m_RecommendedDisplayCIELabValue.getUint16(b, 2);
+    if (result.good())
+        result = m_RecommendedDisplayCIELabValue.getUint16(b, 2);
 
-  return result;
+    return result;
 }
 
-
-OFCondition DcmSegment::getTrackingID(OFString& value,
-                                      const signed long pos)
+OFCondition DcmSegment::getTrackingID(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_TrackingID, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_TrackingID, value, pos);
 }
 
-
-OFCondition DcmSegment::getTrackingUID(OFString& value,
-                                       const signed long pos)
+OFCondition DcmSegment::getTrackingUID(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_TrackingUID, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_TrackingUID, value, pos);
 }
 
-
 // -------------- setters --------------------
 
-
-OFCondition DcmSegment::setSegmentLabel(const OFString& value,
-                                        const OFBool checkValue)
+OFCondition DcmSegment::setSegmentLabel(const OFString& value, const OFBool checkValue)
 {
-  return m_SegmentDescription.setSegmentLabel(value, checkValue);
+    return m_SegmentDescription.setSegmentLabel(value, checkValue);
 }
 
-
-OFCondition DcmSegment::setSegmentDescription(const OFString& value,
-                                              const OFBool checkValue)
+OFCondition DcmSegment::setSegmentDescription(const OFString& value, const OFBool checkValue)
 {
-  return m_SegmentDescription.setSegmentDescription(value, checkValue);
+    return m_SegmentDescription.setSegmentDescription(value, checkValue);
 }
 
-
 OFCondition DcmSegment::setSegmentAlgorithm(const DcmSegTypes::E_SegmentAlgoType algoType,
                                             const OFString& algoName,
                                             const OFBool checkValue)
 {
-  if (checkValue && algoType == DcmSegTypes::SAT_UNKNOWN)
-  {
-    DCMSEG_ERROR("Algorithm type must be initialized to a valid value");
-    return EC_InvalidValue;
-  }
-
-  OFCondition result;
-  // Set algorithm name if algorithm type is not manual (otherwise do not set it at all)
-  if (algoType != DcmSegTypes::SAT_MANUAL)
-  {
-    if ( checkValue && algoName.empty() )
+    if (checkValue && algoType == DcmSegTypes::SAT_UNKNOWN)
+    {
+        DCMSEG_ERROR("Algorithm type must be initialized to a valid value");
+        return EC_InvalidValue;
+    }
+
+    OFCondition result;
+    // Set algorithm name if algorithm type is not manual (otherwise do not set it at all)
+    if (algoType != DcmSegTypes::SAT_MANUAL)
     {
-      DCMSEG_ERROR("Algorithm name must be provided if Algorithm Type is not 'MANUAL'");
-      return EC_MissingValue;
+        if (checkValue && algoName.empty())
+        {
+            DCMSEG_ERROR("Algorithm name must be provided if Algorithm Type is not 'MANUAL'");
+            return EC_MissingValue;
+        }
+        if (!algoName.empty())
+        {
+            result = (checkValue) ? DcmLongString::checkStringValue(algoName, "1") : EC_Normal;
+            if (result.good())
+            {
+                result = m_SegmentAlgorithmName.putOFStringArray(algoName);
+            }
+        }
     }
-    if (!algoName.empty())
+    // Set algorithm type
+    if (result.good())
     {
-      result = (checkValue) ? DcmLongString::checkStringValue(algoName, "1") : EC_Normal;
-      if (result.good())
-      {
-        result = m_SegmentAlgorithmName.putOFStringArray(algoName);
-      }
+        result = m_SegmentDescription.setSegmentAlgorithmType(algoType);
     }
-  }
-  // Set algorithm type
-  if (result.good())
-  {
-   result =  m_SegmentDescription.setSegmentAlgorithmType(algoType);
-  }
-  return result;
+    return result;
 }
 
-
 OFCondition DcmSegment::setSegmentationAlgorithmIdentification(const AlgorithmIdentificationMacro& value,
                                                                const OFBool checkValue)
 {
-  m_SegmentationAlgorithmIdentification = value;
-  OFCondition result;
-  if (checkValue)
-  {
-    result = m_SegmentationAlgorithmIdentification.check();
-  }
-
-  if (result.bad())
-  {
-    m_SegmentationAlgorithmIdentification.clearData();
-  }
+    m_SegmentationAlgorithmIdentification = value;
+    OFCondition result;
+    if (checkValue)
+    {
+        result = m_SegmentationAlgorithmIdentification.check();
+    }
 
-  return result;
-}
+    if (result.bad())
+    {
+        m_SegmentationAlgorithmIdentification.clearData();
+    }
 
+    return result;
+}
 
-OFCondition DcmSegment::setRecommendedDisplayGrayscaleValue(const Uint16 value,
-                                                            const OFBool)
+OFCondition DcmSegment::setRecommendedDisplayGrayscaleValue(const Uint16 value, const OFBool)
 {
-  return m_RecommendedDisplayGrayscaleValue.putUint16(value, 0);
+    return m_RecommendedDisplayGrayscaleValue.putUint16(value, 0);
 }
 
-
-OFCondition DcmSegment::setRecommendedDisplayCIELabValue(const Uint16 r,
-                                                         const Uint16 g,
-                                                         const Uint16 b,
-                                                         const OFBool)
+OFCondition DcmSegment::setRecommendedDisplayCIELabValue(const Uint16 r, const Uint16 g, const Uint16 b, const OFBool)
 {
-  OFCondition result = m_RecommendedDisplayCIELabValue.putUint16(r, 0);
-  if (result.good())
-    result = m_RecommendedDisplayCIELabValue.putUint16(g, 1);
-  if (result.good())
-    result = m_RecommendedDisplayCIELabValue.putUint16(b, 2);
-  return result;
+    OFCondition result = m_RecommendedDisplayCIELabValue.putUint16(r, 0);
+    if (result.good())
+        result = m_RecommendedDisplayCIELabValue.putUint16(g, 1);
+    if (result.good())
+        result = m_RecommendedDisplayCIELabValue.putUint16(b, 2);
+    return result;
 }
 
-
-OFCondition DcmSegment::setTrackingID(const OFString& value,
-                                      const OFBool checkValue)
+OFCondition DcmSegment::setTrackingID(const OFString& value, const OFBool checkValue)
 {
-  // avoid compile warning on unused variable
-  (void)checkValue;
-  return m_TrackingID.putOFStringArray(value);
+    // avoid compile warning on unused variable
+    (void)checkValue;
+    return m_TrackingID.putOFStringArray(value);
 }
 
-
-OFCondition DcmSegment::setTrackingUID(const OFString& value,
-                                       const OFBool checkValue)
+OFCondition DcmSegment::setTrackingUID(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result;
-  if (checkValue)
-  {
-    result = DcmUniqueIdentifier::checkStringValue(value, "1");
-  }
-  if (result.good())
-  {
-    result = m_TrackingUID.putOFStringArray(value);
-  }
-  return result;
+    OFCondition result;
+    if (checkValue)
+    {
+        result = DcmUniqueIdentifier::checkStringValue(value, "1");
+    }
+    if (result.good())
+    {
+        result = m_TrackingUID.putOFStringArray(value);
+    }
+    return result;
 }
 
-
 void DcmSegment::referenceSegmentationDoc(DcmSegmentation* doc)
 {
-  this->m_SegmentationDoc = doc;
+    this->m_SegmentationDoc = doc;
 }
index 43dbf19a9f294b5d143a94b7ea57370a88685fd9..dd1aacce4e143012f4890b05530af436b76ef36f 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2016, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  */
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/dcmdata/dcerror.h"
-#include "dcmtk/dcmiod/iodutil.h"
 #include "dcmtk/dcmiod/iodmacro.h"
+#include "dcmtk/dcmiod/iodutil.h"
 #include "dcmtk/dcmseg/segtypes.h"
 
 OFLogger DCM_dcmsegLogger = OFLog::getLogger("dcmtk.dcmseg");
@@ -32,327 +33,309 @@ OFLogger DCM_dcmsegLogger = OFLog::getLogger("dcmtk.dcmseg");
  *---------------------------------*/
 
 // conditions
-makeOFConditionConst(SG_EC_MaxSegmentsReached,      OFM_dcmseg, 1, OF_error, "Maximum Number of Functional Groups reached");
-makeOFConditionConst(SG_EC_NoSuchSegment,           OFM_dcmseg, 2, OF_error,  "No such segment");
-makeOFConditionConst(SG_EC_UnknownSegmentationType, OFM_dcmseg, 3, OF_error,  "Unknown Segmentation Type");
-makeOFConditionConst(SG_EC_InvalidValue,            OFM_dcmseg, 4, OF_error,  "Invalid value for Segmentation SOP Class");
-makeOFConditionConst(SG_EC_NotEnoughData,           OFM_dcmseg, 5, OF_error,  "Not enough data");
-
+makeOFConditionConst(SG_EC_MaxSegmentsReached, OFM_dcmseg, 1, OF_error, "Maximum Number of Functional Groups reached");
+makeOFConditionConst(SG_EC_NoSuchSegment, OFM_dcmseg, 2, OF_error, "No such segment");
+makeOFConditionConst(SG_EC_UnknownSegmentationType, OFM_dcmseg, 3, OF_error, "Unknown Segmentation Type");
+makeOFConditionConst(SG_EC_InvalidValue, OFM_dcmseg, 4, OF_error, "Invalid value for Segmentation SOP Class");
+makeOFConditionConst(SG_EC_NotEnoughData, OFM_dcmseg, 5, OF_error, "Not enough data");
 
 DcmSegTypes::E_SegmentationType DcmSegTypes::OFString2Segtype(const OFString& value)
 {
-  if (value == "BINARY")
-    return DcmSegTypes::ST_BINARY;
-  if (value == "FRACTIONAL")
-    return DcmSegTypes::ST_FRACTIONAL;
-  else
-    return DcmSegTypes::ST_UNKNOWN;
+    if (value == "BINARY")
+        return DcmSegTypes::ST_BINARY;
+    if (value == "FRACTIONAL")
+        return DcmSegTypes::ST_FRACTIONAL;
+    else
+        return DcmSegTypes::ST_UNKNOWN;
 }
 
-
 OFString DcmSegTypes::segtype2OFString(const DcmSegTypes::E_SegmentationType& value)
 {
-  switch(value)
-  {
-    case DcmSegTypes::ST_BINARY: return "BINARY";
-    case DcmSegTypes::ST_FRACTIONAL: return "FRACTIONAL";
-    case DcmSegTypes::ST_UNKNOWN: return "UNKNOWN";
-    default: return "Invalid segmentation type (internal error)";
-  }
+    switch (value)
+    {
+        case DcmSegTypes::ST_BINARY:
+            return "BINARY";
+        case DcmSegTypes::ST_FRACTIONAL:
+            return "FRACTIONAL";
+        case DcmSegTypes::ST_UNKNOWN:
+            return "UNKNOWN";
+        default:
+            return "Invalid segmentation type (internal error)";
+    }
 }
 
-
 DcmSegTypes::E_SegmentationFractionalType DcmSegTypes::OFString2FractionalType(const OFString& value)
 {
-  if (value == "PROBABILITY")
-    return DcmSegTypes::SFT_PROBABILITY;
-  if (value == "OCCUPANCY")
-    return DcmSegTypes::SFT_OCCUPANCY;
-  else
-    return DcmSegTypes::SFT_UNKNOWN;
+    if (value == "PROBABILITY")
+        return DcmSegTypes::SFT_PROBABILITY;
+    if (value == "OCCUPANCY")
+        return DcmSegTypes::SFT_OCCUPANCY;
+    else
+        return DcmSegTypes::SFT_UNKNOWN;
 }
 
-
-
 OFString DcmSegTypes::algoType2OFString(DcmSegTypes::E_SegmentAlgoType algo)
 {
-  switch (algo)
-  {
-    case SAT_AUTOMATIC: return "AUTOMATIC"; break;
-    case SAT_SEMIAUTOMATIC: return "SEMIAUTOMATIC"; break;
-    case SAT_MANUAL: return "MANUAL"; break;
-    default: return "";
-  }
+    switch (algo)
+    {
+        case SAT_AUTOMATIC:
+            return "AUTOMATIC";
+            break;
+        case SAT_SEMIAUTOMATIC:
+            return "SEMIAUTOMATIC";
+            break;
+        case SAT_MANUAL:
+            return "MANUAL";
+            break;
+        default:
+            return "";
+    }
 }
 
-
 DcmSegTypes::E_SegmentAlgoType DcmSegTypes::OFString2AlgoType(const OFString& algoType)
 {
-  if (algoType == "AUTOMATIC")
-    return DcmSegTypes::SAT_AUTOMATIC;
-  if (algoType == "MANUAL")
-    return DcmSegTypes::SAT_MANUAL;
-  if (algoType == "SEMIAUTOMATIC")
-    return DcmSegTypes::SAT_SEMIAUTOMATIC;
-  else
-    return DcmSegTypes::SAT_UNKNOWN;
+    if (algoType == "AUTOMATIC")
+        return DcmSegTypes::SAT_AUTOMATIC;
+    if (algoType == "MANUAL")
+        return DcmSegTypes::SAT_MANUAL;
+    if (algoType == "SEMIAUTOMATIC")
+        return DcmSegTypes::SAT_SEMIAUTOMATIC;
+    else
+        return DcmSegTypes::SAT_UNKNOWN;
 }
 
-SegmentDescriptionMacro::SegmentDescriptionMacro() :
-  m_SegmentLabel(DCM_SegmentLabel),
-  m_SegmentDescription(DCM_SegmentDescription),
-  m_SegmentAlgorithmType(DcmSegTypes::SAT_UNKNOWN),
-  m_GeneralAnatomyCode("3" /* General Anatomy Optional Macro* */),
-  m_SegmentedPropertyCategoryCode(),
-  m_SegmentedPropertyType()
+SegmentDescriptionMacro::SegmentDescriptionMacro()
+    : m_SegmentLabel(DCM_SegmentLabel)
+    , m_SegmentDescription(DCM_SegmentDescription)
+    , m_SegmentAlgorithmType(DcmSegTypes::SAT_UNKNOWN)
+    , m_GeneralAnatomyCode("3" /* General Anatomy Optional Macro* */)
+    , m_SegmentedPropertyCategoryCode()
+    , m_SegmentedPropertyType()
 {
 }
 
-
 SegmentDescriptionMacro::~SegmentDescriptionMacro()
 {
 }
 
-
 void SegmentDescriptionMacro::clearData()
 {
-  m_SegmentLabel.clear();
-  m_SegmentDescription.clear();
-  m_SegmentAlgorithmType = DcmSegTypes::SAT_UNKNOWN;
-  m_GeneralAnatomyCode.clearData();
-  m_SegmentedPropertyCategoryCode.clearData();
-  m_SegmentedPropertyType.clearData();
+    m_SegmentLabel.clear();
+    m_SegmentDescription.clear();
+    m_SegmentAlgorithmType = DcmSegTypes::SAT_UNKNOWN;
+    m_GeneralAnatomyCode.clearData();
+    m_SegmentedPropertyCategoryCode.clearData();
+    m_SegmentedPropertyType.clearData();
 }
 
-
 OFCondition SegmentDescriptionMacro::read(DcmItem& item)
 {
-  /* re-initialize object */
-  clearData();
+    /* re-initialize object */
+    clearData();
 
-  DcmIODUtil::getAndCheckElementFromDataset(item, m_SegmentLabel, "1", "1", "SegmentDescriptionMacro");
-  DcmIODUtil::getAndCheckElementFromDataset(item, m_SegmentDescription, "1", "3", "SegmentDescriptionMacro");
-  readSegmentAlgorithmType(item);
-  m_GeneralAnatomyCode.read(item);
-  DcmIODUtil::readSingleItem<CodeSequenceMacro>(item, DCM_SegmentedPropertyCategoryCodeSequence, m_SegmentedPropertyCategoryCode, "1", "SegmentDescriptionMacro");
-  DcmIODUtil::readSingleItem<SegmentedPropertyTypeCodeItem>(item, DCM_SegmentedPropertyTypeCodeSequence, m_SegmentedPropertyType, "1", "SegmentDescriptionMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_SegmentLabel, "1", "1", "SegmentDescriptionMacro");
+    DcmIODUtil::getAndCheckElementFromDataset(item, m_SegmentDescription, "1", "3", "SegmentDescriptionMacro");
+    readSegmentAlgorithmType(item);
+    m_GeneralAnatomyCode.read(item);
+    DcmIODUtil::readSingleItem<CodeSequenceMacro>(item,
+                                                  DCM_SegmentedPropertyCategoryCodeSequence,
+                                                  m_SegmentedPropertyCategoryCode,
+                                                  "1",
+                                                  "SegmentDescriptionMacro");
+    DcmIODUtil::readSingleItem<SegmentedPropertyTypeCodeItem>(
+        item, DCM_SegmentedPropertyTypeCodeSequence, m_SegmentedPropertyType, "1", "SegmentDescriptionMacro");
 
-  return EC_Normal;
+    return EC_Normal;
 }
 
-
 OFCondition SegmentDescriptionMacro::write(DcmItem& item)
 {
-  OFCondition result = EC_Normal;
-
-  /* copy all elements to dataset */
-  DcmIODUtil::copyElementToDataset(result, item, m_SegmentLabel, "1" /* VM */, "1" /* Type */, "SegmentDescriptionMacro");
-  DcmIODUtil::copyElementToDataset(result, item, m_SegmentDescription, "1", "3", "SegmentDescriptionMacro");
-  if (result.good()) result = writeSegmentAlgorithmType(item);
-  if (result.good())
-  {
-    if (m_GeneralAnatomyCode.check(OFTrue /* quiet */).good())
+    OFCondition result = EC_Normal;
+
+    /* copy all elements to dataset */
+    DcmIODUtil::copyElementToDataset(
+        result, item, m_SegmentLabel, "1" /* VM */, "1" /* Type */, "SegmentDescriptionMacro");
+    DcmIODUtil::copyElementToDataset(result, item, m_SegmentDescription, "1", "3", "SegmentDescriptionMacro");
+    if (result.good())
+        result = writeSegmentAlgorithmType(item);
+    if (result.good())
     {
-      result = m_GeneralAnatomyCode.write(item);
+        if (m_GeneralAnatomyCode.check(OFTrue /* quiet */).good())
+        {
+            result = m_GeneralAnatomyCode.write(item);
+        }
     }
-  }
-  DcmIODUtil::writeSingleItem<CodeSequenceMacro>(result, DCM_SegmentedPropertyCategoryCodeSequence, m_SegmentedPropertyCategoryCode, item, "1", "SegmentDescriptionMacro");
-  DcmIODUtil::writeSingleItem<SegmentedPropertyTypeCodeItem>(result, DCM_SegmentedPropertyTypeCodeSequence, m_SegmentedPropertyType, item, "1", "SegmentDescriptionMacro");
-  return result;
+    DcmIODUtil::writeSingleItem<CodeSequenceMacro>(result,
+                                                   DCM_SegmentedPropertyCategoryCodeSequence,
+                                                   m_SegmentedPropertyCategoryCode,
+                                                   item,
+                                                   "1",
+                                                   "SegmentDescriptionMacro");
+    DcmIODUtil::writeSingleItem<SegmentedPropertyTypeCodeItem>(
+        result, DCM_SegmentedPropertyTypeCodeSequence, m_SegmentedPropertyType, item, "1", "SegmentDescriptionMacro");
+    return result;
 }
 
-
-OFCondition SegmentDescriptionMacro::getSegmentLabel(OFString& value,
-                                                     const signed long pos)
+OFCondition SegmentDescriptionMacro::getSegmentLabel(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_SegmentLabel, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_SegmentLabel, value, pos);
 }
 
-
-OFCondition SegmentDescriptionMacro::getSegmentDescription(OFString& value,
-                                                           const signed long pos)
+OFCondition SegmentDescriptionMacro::getSegmentDescription(OFString& value, const signed long pos)
 {
-  return DcmIODUtil::getStringValueFromElement(m_SegmentDescription, value, pos);
+    return DcmIODUtil::getStringValueFromElement(m_SegmentDescription, value, pos);
 }
 
-
 DcmSegTypes::E_SegmentAlgoType SegmentDescriptionMacro::getSegmentAlgorithmType()
 {
-  return m_SegmentAlgorithmType;
+    return m_SegmentAlgorithmType;
 }
 
-
 GeneralAnatomyMacro& SegmentDescriptionMacro::getGeneralAnatomyCode()
 {
-  return m_GeneralAnatomyCode;
+    return m_GeneralAnatomyCode;
 }
 
-
 CodeSequenceMacro& SegmentDescriptionMacro::getSegmentedPropertyCategoryCode()
 {
-  return m_SegmentedPropertyCategoryCode;
+    return m_SegmentedPropertyCategoryCode;
 }
 
-
 CodeSequenceMacro& SegmentDescriptionMacro::getSegmentedPropertyTypeCode()
 {
-  return m_SegmentedPropertyType.m_SegmentedPropertyTypeCode;
+    return m_SegmentedPropertyType.m_SegmentedPropertyTypeCode;
 }
 
-
-OFVector< CodeSequenceMacro* >& SegmentDescriptionMacro::getSegmentedPropertyTypeModifier()
+OFVector<CodeSequenceMacro*>& SegmentDescriptionMacro::getSegmentedPropertyTypeModifier()
 {
-  return m_SegmentedPropertyType.m_SegmentedPropertyTypeModifierCode;
+    return m_SegmentedPropertyType.m_SegmentedPropertyTypeModifierCode;
 }
 
-
-OFCondition SegmentDescriptionMacro::setSegmentLabel(const OFString& value,
-                                                     const OFBool checkValue)
+OFCondition SegmentDescriptionMacro::setSegmentLabel(const OFString& value, const OFBool checkValue)
 {
-  OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
-  if (result.good())
-    result = m_SegmentLabel.putOFStringArray(value);
-  return result;
+    OFCondition result = (checkValue) ? DcmLongString::checkStringValue(value, "1") : EC_Normal;
+    if (result.good())
+        result = m_SegmentLabel.putOFStringArray(value);
+    return result;
 }
 
-
-OFCondition SegmentDescriptionMacro::setSegmentDescription(const OFString& value,
-                                                           const OFBool checkValue)
+OFCondition SegmentDescriptionMacro::setSegmentDescription(const OFString& value, const OFBool checkValue)
 {
-  (void)checkValue;
-  return  m_SegmentDescription.putOFStringArray(value);
+    (void)checkValue;
+    return m_SegmentDescription.putOFStringArray(value);
 }
 
-
 OFCondition SegmentDescriptionMacro::setSegmentAlgorithmType(const DcmSegTypes::E_SegmentAlgoType value)
 {
-  m_SegmentAlgorithmType = value;
-  return EC_Normal;
+    m_SegmentAlgorithmType = value;
+    return EC_Normal;
 }
 
-
 OFCondition SegmentDescriptionMacro::readSegmentAlgorithmType(DcmItem& item)
 {
-  DcmCodeString element(DCM_SegmentAlgorithmType);
-  OFCondition result = DcmIODUtil::getAndCheckElementFromDataset(item, element, "1", "1", "SegmentDescriptionMacro");
-  OFString str;
-  if (result.good())
-  {
-    element.getOFStringArray(str);
-    m_SegmentAlgorithmType = DcmSegTypes::OFString2AlgoType(str);
-  }
-
-  if (m_SegmentAlgorithmType == DcmSegTypes::SAT_UNKNOWN)
-  {
-    DCMSEG_ERROR("Invalid value for attribute Segmentation Algorithm Type: " << str);
-    return SG_EC_InvalidValue;
-  }
-  else
-    return EC_Normal;
-}
+    DcmCodeString element(DCM_SegmentAlgorithmType);
+    OFCondition result = DcmIODUtil::getAndCheckElementFromDataset(item, element, "1", "1", "SegmentDescriptionMacro");
+    OFString str;
+    if (result.good())
+    {
+        element.getOFStringArray(str);
+        m_SegmentAlgorithmType = DcmSegTypes::OFString2AlgoType(str);
+    }
 
+    if (m_SegmentAlgorithmType == DcmSegTypes::SAT_UNKNOWN)
+    {
+        DCMSEG_ERROR("Invalid value for attribute Segmentation Algorithm Type: " << str);
+        return SG_EC_InvalidValue;
+    }
+    else
+        return EC_Normal;
+}
 
 OFCondition SegmentDescriptionMacro::writeSegmentAlgorithmType(DcmItem& item)
 {
-  if (m_SegmentAlgorithmType == DcmSegTypes::SAT_UNKNOWN)
-  {
-    DCMSEG_ERROR("Segment Algorithm Type not set");
-    return SG_EC_InvalidValue;
-  }
-
-  OFString str = DcmSegTypes::algoType2OFString(m_SegmentAlgorithmType);
-  return item.putAndInsertOFStringArray(DCM_SegmentAlgorithmType, str);
-}
+    if (m_SegmentAlgorithmType == DcmSegTypes::SAT_UNKNOWN)
+    {
+        DCMSEG_ERROR("Segment Algorithm Type not set");
+        return SG_EC_InvalidValue;
+    }
 
+    OFString str = DcmSegTypes::algoType2OFString(m_SegmentAlgorithmType);
+    return item.putAndInsertOFStringArray(DCM_SegmentAlgorithmType, str);
+}
 
-SegmentedPropertyTypeCodeItem::SegmentedPropertyTypeCodeItem() :
-  m_SegmentedPropertyTypeCode(),
-  m_SegmentedPropertyTypeModifierCode()
+SegmentedPropertyTypeCodeItem::SegmentedPropertyTypeCodeItem()
+    : m_SegmentedPropertyTypeCode()
+    , m_SegmentedPropertyTypeModifierCode()
 {
-
 }
 
-
 SegmentedPropertyTypeCodeItem::~SegmentedPropertyTypeCodeItem()
 {
-  DcmIODUtil::freeContainer(m_SegmentedPropertyTypeModifierCode);
+    DcmIODUtil::freeContainer(m_SegmentedPropertyTypeModifierCode);
 }
 
-
 OFCondition SegmentedPropertyTypeCodeItem::check(const OFBool quiet)
 {
-  OFCondition result = m_SegmentedPropertyTypeCode.check(quiet);
-  if (result.good())
-  {
-    result = checkModifiers(quiet);
-  }
-  return result;
+    OFCondition result = m_SegmentedPropertyTypeCode.check(quiet);
+    if (result.good())
+    {
+        result = checkModifiers(quiet);
+    }
+    return result;
 }
 
-
 OFCondition SegmentedPropertyTypeCodeItem::checkModifiers(const OFBool quiet)
 {
-  OFCondition result;
-  OFVector<CodeSequenceMacro*>::iterator it = m_SegmentedPropertyTypeModifierCode.begin();
-  while (it != m_SegmentedPropertyTypeModifierCode.end())
-  {
-    result = (*it)->check(quiet);
-    if (result.bad())
-      return result;
-    it++;
-  }
-  return EC_Normal;
+    OFCondition result;
+    OFVector<CodeSequenceMacro*>::iterator it = m_SegmentedPropertyTypeModifierCode.begin();
+    while (it != m_SegmentedPropertyTypeModifierCode.end())
+    {
+        result = (*it)->check(quiet);
+        if (result.bad())
+            return result;
+        it++;
+    }
+    return EC_Normal;
 }
 
-
 void SegmentedPropertyTypeCodeItem::clearData()
 {
-  DcmIODUtil::freeContainer(m_SegmentedPropertyTypeModifierCode);
-  m_SegmentedPropertyTypeCode.clearData();
+    DcmIODUtil::freeContainer(m_SegmentedPropertyTypeModifierCode);
+    m_SegmentedPropertyTypeCode.clearData();
 }
 
-
-OFCondition SegmentedPropertyTypeCodeItem::read(DcmItem& item,
-                                                const OFBool clearOldData)
+OFCondition SegmentedPropertyTypeCodeItem::read(DcmItem& item, const OFBool clearOldData)
 {
-  OFCondition result;
-  if (clearOldData)
-    clearData();
-
-  m_SegmentedPropertyTypeCode.read(item);
-  DcmIODUtil::readSubSequence
-  (
-    item,
-    DCM_SegmentedPropertyTypeModifierCodeSequence,
-    m_SegmentedPropertyTypeModifierCode,
-    "1-n",
-    "3",
-    "SegmentDescriptionMacro"
-  );
-  return result;
+    OFCondition result;
+    if (clearOldData)
+        clearData();
+
+    m_SegmentedPropertyTypeCode.read(item);
+    DcmIODUtil::readSubSequence(item,
+                                DCM_SegmentedPropertyTypeModifierCodeSequence,
+                                m_SegmentedPropertyTypeModifierCode,
+                                "1-n",
+                                "3",
+                                "SegmentDescriptionMacro");
+    return result;
 }
 
-
-
 OFCondition SegmentedPropertyTypeCodeItem::write(DcmItem& item)
 {
-  OFCondition result = m_SegmentedPropertyTypeCode.write(item);
-  if (result.good())
-  {
-    result = checkModifiers();
+    OFCondition result = m_SegmentedPropertyTypeCode.write(item);
     if (result.good())
     {
-      DcmIODUtil::writeSubSequence<OFVector<CodeSequenceMacro*> >
-      (
-       result,
-       DCM_SegmentedPropertyTypeModifierCodeSequence,
-       m_SegmentedPropertyTypeModifierCode,
-       item,
-       "1-n",
-       "3",
-       "SegmentDescriptionMacro"
-      );
+        result = checkModifiers();
+        if (result.good())
+        {
+            DcmIODUtil::writeSubSequence<OFVector<CodeSequenceMacro*> >(result,
+                                                                        DCM_SegmentedPropertyTypeModifierCodeSequence,
+                                                                        m_SegmentedPropertyTypeModifierCode,
+                                                                        item,
+                                                                        "1-n",
+                                                                        "3",
+                                                                        "SegmentDescriptionMacro");
+        }
     }
-  }
-  return result;
+    return result;
 }
index b2b647c480ecbac7802e810b4c16809f2e9cc377..509cf02775f1052d045ac085f5c4d4a0b81f1c9f 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, Open Connections GmbH
+ *  Copyright (C) 2015-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
  */
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmseg/segutils.h"
-#include "dcmtk/dcmseg/segdef.h"
 
+#include "dcmtk/dcmiod/iodutil.h"
+#include "dcmtk/dcmseg/segdef.h"
+#include "dcmtk/dcmseg/segutils.h"
 
-DcmIODTypes::Frame* DcmSegUtils::packBinaryFrame(const Uint8* pixelData,
-                                                 const Uint16 rows,
-                                                 const Uint16 columns)
+DcmIODTypes::Frame* DcmSegUtils::packBinaryFrame(const Uint8* pixelData, const Uint16 rows, const Uint16 columns)
 {
-  // Sanity checking
-  const size_t numPixels = OFstatic_cast(size_t, rows) * columns;
-  if (numPixels == 0)
-  {
-    DCMSEG_ERROR("Unable to pack binary segmentation frame: Rows or Columns is 0");
-    return NULL;
-  }
-  if (!pixelData)
-  {
-    DCMSEG_ERROR("Unable to pack binary segmentation frame: No pixel data provided");
-    return NULL;
-  }
-  DcmIODTypes::Frame* frame = new DcmIODTypes::Frame();
-  if (frame == NULL)
-  {
-    DCMSEG_ERROR("Could not pack binary segmentation frame: Memory exhausted");
-    return NULL;
-  }
-  frame->length = getBytesForBinaryFrame(numPixels);
-  frame->pixData = new Uint8[frame->length];
-  if (frame->pixData == 0)
-  {
-    delete frame;
-    return NULL;
-  }
-  memset(frame->pixData, 0, frame->length);
+    // Sanity checking
+    const size_t numPixels = OFstatic_cast(size_t, rows) * columns;
+    if (numPixels == 0)
+    {
+        DCMSEG_ERROR("Unable to pack binary segmentation frame: Rows or Columns is 0");
+        return NULL;
+    }
+    if (!pixelData)
+    {
+        DCMSEG_ERROR("Unable to pack binary segmentation frame: No pixel data provided");
+        return NULL;
+    }
+    DcmIODTypes::Frame* frame = new DcmIODTypes::Frame();
+    if (frame == NULL)
+    {
+        DCMSEG_ERROR("Could not pack binary segmentation frame: Memory exhausted");
+        return NULL;
+    }
+    frame->length  = getBytesForBinaryFrame(numPixels);
+    frame->pixData = new Uint8[frame->length];
+    if (frame->pixData == 0)
+    {
+        delete frame;
+        return NULL;
+    }
+    memset(frame->pixData, 0, frame->length);
 
-  size_t bytePos = 0;
-  for (size_t count = 0; count < numPixels; count++)
-  {
-    // Compute byte position
-    bytePos = count / 8;
-    frame->pixData[bytePos] |= (pixelData[count] != 0) /* value to set */ << (count % 8 /* bit position (0-7) within byte */);
-  }
-  return frame;
+    size_t bytePos = 0;
+    for (size_t count = 0; count < numPixels; count++)
+    {
+        // Compute byte position
+        bytePos = count / 8;
+        frame->pixData[bytePos]
+            |= (pixelData[count] != 0) /* value to set */ << (count % 8 /* bit position (0-7) within byte */);
+    }
+    return frame;
 }
 
-
-DcmIODTypes::Frame* DcmSegUtils::unpackBinaryFrame(const DcmIODTypes::Frame* frame,
-                                                   Uint16 rows,
-                                                   Uint16 cols)
+DcmIODTypes::Frame* DcmSegUtils::unpackBinaryFrame(const DcmIODTypes::Frame* frame, Uint16 rows, Uint16 cols)
 {
-  // Sanity checking
-  if ( (frame == NULL) || (rows == 0) || (cols == 0) )
-  {
-    DCMSEG_ERROR("Cannot unpack binary frame, invalid input data");
-    return NULL;
-  }
-
-  // Create result frame in memory
-  size_t numBits = OFstatic_cast(size_t, rows) * cols;
-  DcmIODTypes::Frame* result = new DcmIODTypes::Frame();
-  if (result)
-  {
-    result->pixData = new Uint8[numBits];
-    if (!result->pixData)
+    // Sanity checking
+    if ((frame == NULL) || (rows == 0) || (cols == 0))
     {
-        delete result;
+        DCMSEG_ERROR("Cannot unpack binary frame, invalid input data");
         return NULL;
     }
-    result->length = numBits;
-  }
-  if ( !result || !(result->pixData) )
-  {
-    DCMSEG_ERROR("Cannot unpack binary frame, memory exhausted");
-    return NULL;
-  }
-  memset(result->pixData, 0, result->length);
 
-  // Transform and copy from packed frame to unpacked result frame
-  size_t bytePos = 0;
-  for (size_t count = 0; count < numBits; count++)
-  {
-    // Compute byte position
-    bytePos = count / 8;
-    // Bit position (0-7) within byte
-    Uint8 bitpos = (count % 8);
-    if ( (frame->pixData[bytePos] & (1 << bitpos) /* check whether bit at bitpos is set*/) )
+    // Create result frame in memory
+    size_t numBits             = OFstatic_cast(size_t, rows) * cols;
+    DcmIODTypes::Frame* result = new DcmIODTypes::Frame();
+    if (result)
     {
-      result->pixData[count] = 1;
+        result->pixData = new Uint8[numBits];
+        if (!result->pixData)
+        {
+            delete result;
+            return NULL;
+        }
+        result->length = numBits;
     }
-    else
+    if (!result || !(result->pixData))
     {
-      result->pixData[count] = 0;
+        DCMSEG_ERROR("Cannot unpack binary frame, memory exhausted");
+        return NULL;
     }
-  }
-  return result;
-}
+    memset(result->pixData, 0, result->length);
 
+    // Transform and copy from packed frame to unpacked result frame
+    size_t bytePos = 0;
+    for (size_t count = 0; count < numBits; count++)
+    {
+        // Compute byte position
+        bytePos = count / 8;
+        // Bit position (0-7) within byte
+        Uint8 bitpos = (count % 8);
+        if ((frame->pixData[bytePos] & (1 << bitpos) /* check whether bit at bitpos is set*/))
+        {
+            result->pixData[count] = 1;
+        }
+        else
+        {
+            result->pixData[count] = 0;
+        }
+    }
+    return result;
+}
 
 size_t DcmSegUtils::getBytesForBinaryFrame(const size_t& numPixels)
 {
-  // check whether the 1-bit pixels exactly fit into bytes
-  size_t remainder = numPixels % 8;
-  // number of bytes that work on an exact fit
-  size_t bytesRequired =  numPixels / 8;
-  // add one byte if we have a remainder
-  if (remainder > 0) bytesRequired++;
-  return bytesRequired;
+    // check whether the 1-bit pixels exactly fit into bytes
+    size_t remainder = numPixels % 8;
+    // number of bytes that work on an exact fit
+    size_t bytesRequired = numPixels / 8;
+    // add one byte if we have a remainder
+    if (remainder > 0)
+        bytesRequired++;
+    return bytesRequired;
 }
 
-
-void DcmSegUtils::alignFrameOnBitPosition(Uint8* buf,
-                                          size_t bufLen,
-                                          Uint8 numBits)
+void DcmSegUtils::alignFrameOnBitPosition(Uint8* buf, const size_t bufLen, const Uint8 numBits)
 {
-  if (numBits > 7)
-  {
-    DCMSEG_ERROR("Invalid input data: shiftFrameBitsLeft() can only shift 0-7 bits");
-    return;
-  }
-  Uint8 carryOver = 0;
-  for (size_t x = 0; x < bufLen; x++)
-  {
-    // Store current byte since we need to restore its first bits later
-    Uint8 current = buf[x];
-    // Shift pixels given num bits to the left, creating (8 - num bits)
-    // empty bits at the right
-    buf[x] <<= numBits;
-    // If there is a carry over from the previous byte, add it in again (will always be at the end,
-    // see carry over calculation in next step)
-    buf[x] |= carryOver;
-    // Compute carry over bits for next byte to be handled, i.e. those bits at the left that will be
-    // overwritten in the next byte
-    carryOver = current >> (8-numBits);
-  }
+    if (numBits > 7)
+    {
+        DCMSEG_ERROR("Invalid input data: shiftFrameBitsLeft() can only shift 0-7 bits");
+        return;
+    }
+    Uint8 carryOver = 0;
+    for (size_t x = 0; x < bufLen; x++)
+    {
+        // Store current byte since we need to restore its first bits later
+        Uint8 current = buf[x];
+        // Shift pixels given num bits to the left, creating (8 - num bits)
+        // empty bits at the right
+        buf[x] <<= numBits;
+        // If there is a carry over from the previous byte, add it in again (will always be at the end,
+        // see carry over calculation in next step)
+        buf[x] |= carryOver;
+        // Compute carry over bits for next byte to be handled, i.e. those bits at the left that will be
+        // overwritten in the next byte
+        carryOver = current >> (8 - numBits);
+    }
 }
 
-
-void DcmSegUtils::alignFrameOnByteBoundary(Uint8* buf,
-                                           size_t bufLen,
-                                           Uint8 numBits)
+void DcmSegUtils::alignFrameOnByteBoundary(Uint8* buf, const size_t bufLen, const Uint8 numBits)
 {
-  if (numBits > 7)
-  {
-    DCMSEG_ERROR("Invalid input data: alignFrameOnByteBoundary() can only shift 0-7 bits");
-    return;
-  }
-  for (size_t x = 0; x < bufLen-1; x++)
-  {
-    // Shift current byte
-    buf[x] = buf[x] >> numBits;
-    // isolate portion of next byte that must be shifted into current byte
-    Uint8 next = (buf[x+1] << (8-numBits));
-    // Take over portion from next byte
-    buf[x] |= next;
-  }
-  // Shift last byte manually
-  buf[bufLen-1] >>= numBits;
+    return DcmIODUtil::alignFrameOnByteBoundary(buf, bufLen, numBits);
 }
 
-
-void DcmSegUtils::debugDumpBin(Uint8* buffer,
-                               size_t length,
-                               const char* what)
+void DcmSegUtils::debugDumpBin(Uint8* buffer, size_t length, const char* what)
 {
-  for (size_t n=0; n<length; n++)
-  {
-    DCMSEG_DEBUG(what << " #" << n << ": " << OFstatic_cast(size_t,(buffer[n]))
-      << ", bytepos " << &(buffer[n]) << " (" << debugByte2Bin((buffer[n])) << ")");
-  }
-  DCMSEG_DEBUG("");
+    for (size_t n = 0; n < length; n++)
+    {
+        DCMSEG_DEBUG(what << " #" << n << ": " << OFstatic_cast(size_t, (buffer[n])) << ", bytepos " << &(buffer[n])
+                          << " (" << debugByte2Bin((buffer[n])) << ")");
+    }
+    DCMSEG_DEBUG("");
 }
 
-
 OFString DcmSegUtils::debugByte2Bin(Uint8 b)
 {
-  OFString result("",8);
-  for (int i = 7; i >= 0; i--)
-  {
-    result[i]= (b & 1) + '0';
+    OFString result("", 8);
+    for (int i = 7; i >= 0; i--)
+    {
+        result[i] = (b & 1) + '0';
 
-    b >>= 1;
-  }
-  return result;
+        b >>= 1;
+    }
+    return result;
 }
index 75e108dfd2abc46a8b853c6555a2db33e9613440..61b8e20a1dadd67f5eb11dd618cbafc692135f2b 100644 (file)
@@ -1,5 +1,5 @@
 # declare executables
-DCMTK_ADD_EXECUTABLE(dcmseg_tests tests tutils)
+DCMTK_ADD_EXECUTABLE(dcmseg_tests tests tutils troundtrip.cc tconcat_binary)
 
 # make sure executables are linked to the corresponding libraries
 DCMTK_TARGET_LINK_MODULES(dcmseg_tests dcmseg dcmfg dcmiod dcmdata oflog ofstd)
index b994592744d11ef66c1d4cf2eefb4a2c9dc801f4..e10a91ed727243f776f272ea912885648bba8651 100644 (file)
@@ -1,3 +1,175 @@
+tconcat_binary.o: tconcat_binary.cc \
+ ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmfg/include/dcmtk/dcmfg/concatenationcreator.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmfg/include/dcmtk/dcmfg/concatenationloader.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../ofstd/include/dcmtk/ofstd/oftuple.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdiag.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/push.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/mmtag.def \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefrd.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuple.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/pop.def \
+ ../include/dcmtk/dcmseg/segdoc.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgfracon.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgbase.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fginterface.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodimage.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodcommn.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modpatient.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modpatientstudy.h \
+ ../../ofstd/include/dcmtk/ofstd/ofoption.h \
+ ../../ofstd/include/dcmtk/ofstd/ofalign.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modsopcommon.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralimage.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixelvariant.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixelbase.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvriant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/variant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/helpers.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/cnvrsn.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/vsprfw.def \
+ ../../dcmiod/include/dcmtk/dcmiod/modenhequipment.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixel.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modmultiframedimension.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modmultiframefg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modsegmentationseries.h \
+ ../include/dcmtk/dcmseg/segdef.h ../include/dcmtk/dcmseg/segtypes.h \
+ ../include/dcmtk/dcmseg/segment.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h
 tests.o: tests.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/oftest.h \
  ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
@@ -47,31 +219,203 @@ tests.o: tests.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h
-tutils.o: tutils.cc ../../config/include/dcmtk/config/osconfig.h \
- ../../ofstd/include/dcmtk/ofstd/oftest.h \
- ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
- ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+troundtrip.o: troundtrip.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmseg/segdoc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
  ../../ofstd/include/dcmtk/ofstd/ofexport.h \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
- ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
- ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
  ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmfg/include/dcmtk/dcmfg/concatenationcreator.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
  ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixseq.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcofsetl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrae.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrur.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcchrstr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrlt.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpn.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsh.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrst.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruc.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrut.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpixel.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrpobw.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcovlay.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrss.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrus.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrsv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvruv.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrfd.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrof.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrod.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
+ ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgdefine.h \
+ ../../dcmfg/include/dcmtk/dcmfg/concatenationloader.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../ofstd/include/dcmtk/ofstd/oftuple.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdiag.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/push.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/mmtag.def \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefrd.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuple.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/pop.def \
+ ../../dcmfg/include/dcmtk/dcmfg/fgfracon.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgbase.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgtypes.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fginterface.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodimage.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodcommn.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modpatient.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modpatientstudy.h \
+ ../../ofstd/include/dcmtk/ofstd/ofoption.h \
+ ../../ofstd/include/dcmtk/ofstd/ofalign.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modsopcommon.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralimage.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixelvariant.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixelbase.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvriant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/variant.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/helpers.h \
+ ../../ofstd/include/dcmtk/ofstd/diag/cnvrsn.def \
+ ../../ofstd/include/dcmtk/ofstd/diag/vsprfw.def \
+ ../../dcmiod/include/dcmtk/dcmiod/modenhequipment.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modimagepixel.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modmultiframedimension.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modmultiframefg.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modsegmentationseries.h \
+ ../include/dcmtk/dcmseg/segdef.h ../include/dcmtk/dcmseg/segtypes.h \
+ ../include/dcmtk/dcmseg/segment.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
  ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgpixmsr.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgplanor.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgplanpo.h \
+ ../../dcmfg/include/dcmtk/dcmfg/fgseg.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstrutl.h \
+ ../../ofstd/include/dcmtk/ofstd/oftempf.h
+tutils.o: tutils.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
  ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
  ../../ofstd/include/dcmtk/ofstd/oflimits.h \
  ../../config/include/dcmtk/config/arith.h \
  ../../ofstd/include/dcmtk/ofstd/oferror.h \
- ../../ofstd/include/dcmtk/ofstd/ofexit.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
  ../../oflog/include/dcmtk/oflog/config.h \
@@ -96,36 +440,42 @@ tutils.o: tutils.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
+ ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../include/dcmtk/dcmseg/segutils.h ../include/dcmtk/dcmseg/segdef.h \
  ../include/dcmtk/dcmseg/segtypes.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcistrma.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcostrma.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
  ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcmetinf.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdicdir.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdirrec.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrulup.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrul.h \
@@ -136,11 +486,9 @@ tutils.o: tutils.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvras.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrcs.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrda.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrds.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrdt.h \
  ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvris.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrtm.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrui.h \
@@ -170,8 +518,10 @@ tutils.o: tutils.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
- ../../dcmiod/include/dcmtk/dcmiod/modbase.h
+ ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
+ ../../ofstd/include/dcmtk/ofstd/oftest.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconapp.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcmdln.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexbl.h \
+ ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h
index 12ce44f30c1ffa772d517b6ad1779ee919e180c3..55b7bfd77fc341936902e9c45f78eab9349cceb2 100644 (file)
@@ -25,7 +25,7 @@ LOCALLIBS = -ldcmseg -ldcmfg -ldcmiod -ldcmdata -loflog -lofstd $(ZLIBLIBS) \
 LOCALINCLUDES = -I$(top_srcdir)/include -I$(ofstddir)/include -I$(oflogdir)/include \
        -I$(dcmdatadir)/include -I$(dcmioddir)/include -I$(dcmfgdir)/include \
 
-test_objs = tests.o tutils.o
+test_objs = tconcat_binary.o tests.o troundtrip.o tutils.o
 objs = $(test_objs)
 progs = tests
 
@@ -37,10 +37,10 @@ tests: $(test_objs)
 
 
 check: tests
-       ./tests
+       DCMDICTPATH=../../dcmdata/data/dicom.dic ./tests
 
 check-exhaustive: tests
-       ./tests -x
+       DCMDICTPATH=../../dcmdata/data/dicom.dic ./tests -x
 
 
 install: all
diff --git a/dcmseg/tests/tconcat_binary.cc b/dcmseg/tests/tconcat_binary.cc
new file mode 100644 (file)
index 0000000..5d9224b
--- /dev/null
@@ -0,0 +1,121 @@
+/*
+ *
+ *  Copyright (C) 2019, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmseg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Test for creating, writing and reading binary Segmentation objects
+ *
+ */
+
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+
+#include "dcmtk/dcmfg/concatenationcreator.h"
+#include "dcmtk/dcmfg/concatenationloader.h"
+#include "dcmtk/dcmseg/segdoc.h"
+#include "dcmtk/dcmseg/segment.h"
+#include "dcmtk/ofstd/oftest.h"
+
+const OFString ATLAS_FILE          = "/home/michael/data/dcm/seg_atlas.dcm";
+const size_t NUM_FRAMES_PER_CONCAT = 24;
+
+OFTEST(dcmseg_concat_binary)
+{
+    if (!OFStandard::fileExists(ATLAS_FILE))
+    {
+        DCMSEG_DEBUG("Will not run dcmseg_concat_binary test, input file " << ATLAS_FILE << " missing");
+        return;
+    }
+    /* make sure data dictionary is loaded */
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK(dcmDataDict.isDictionaryLoaded());
+        return;
+    }
+
+    // Loading
+    DcmSegmentation* seg = NULL;
+    OFCondition result   = DcmSegmentation::loadFile(ATLAS_FILE, seg);
+    if (result.good())
+    {
+        ConcatenationCreator cc;
+        result = cc.setCfgFramesPerInstance(NUM_FRAMES_PER_CONCAT);
+        if (result.good())
+        {
+            seg->setCheckFGOnWrite(OFFalse);
+            result = seg->writeConcatenation(cc);
+            if (result.good())
+            {
+                size_t n = 0;
+                do
+                {
+                    OFStringStream ss;
+                    ss << "/tmp/concat_" << n;
+                    result = cc.writeNextInstance(ss.str().c_str());
+                    n++;
+                } while (result.good());
+                if (result != FG_EC_ConcatenationComplete)
+                {
+                    DCMSEG_ERROR("Could not write concatentation instance: " << result.text());
+                    OFCHECK(result.good());
+                }
+            }
+            else
+            {
+                DCMSEG_ERROR("Could not write concatentation: " << result.text());
+                OFCHECK(result.good());
+            }
+        }
+        else
+        {
+            DCMSEG_ERROR("Could not configure concatentation number of frames to " << NUM_FRAMES_PER_CONCAT << ": "
+                                                                                   << result.text());
+            OFCHECK(result.good());
+        }
+    }
+    delete seg;
+    seg = NULL;
+
+    if (result == FG_EC_ConcatenationComplete)
+    {
+        ConcatenationLoader cl;
+        result = cl.scan("/tmp", "concat*", OFFalse);
+        if (result.good())
+        {
+            if (cl.getInfo().size() == 1)
+            {
+                OFVector<DcmIODTypes::Frame*> frames;
+                DcmFileFormat dcmff;
+                result = DcmSegmentation::loadConcatenation(cl, cl.getInfo().begin()->first, seg);
+                if (result.good())
+                {
+                    seg->setCheckFGOnWrite(OFFalse);
+                    result = seg->saveFile("/tmp/atlas_copy.dcm", EXS_LittleEndianExplicit);
+                    if (result.bad())
+                    {
+                        DCMSEG_ERROR("Unable to write re-assembled Concatenation Source instance: " << result.text());
+                        OFCHECK(result.good());
+                    }
+                }
+                delete seg;
+            }
+            else
+            {
+                DCMSEG_ERROR("Unable to load concatenation: Expected 1 but found "
+                             << cl.getInfo().size() << " concatenations in directory /tmp");
+                OFCHECK(cl.getInfo().size() > 1);
+            }
+        }
+    }
+}
index 6e7b462627be5c8fd376c8dd197ac7b705333894..e9cb54e1e1262c93308e607b5b3d3d861c8689e6 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015, OFFIS e.V.
+ *  Copyright (C) 2015-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
  */
 
 #include "dcmtk/config/osconfig.h"
+
 #include "dcmtk/ofstd/oftest.h"
 
 OFTEST_REGISTER(dcmseg_utils);
+OFTEST_REGISTER(dcmseg_roundtrip);
+OFTEST_REGISTER(dcmseg_concat_binary);
+
 OFTEST_MAIN("dcmseg")
diff --git a/dcmseg/tests/troundtrip.cc b/dcmseg/tests/troundtrip.cc
new file mode 100644 (file)
index 0000000..472eaf1
--- /dev/null
@@ -0,0 +1,1041 @@
+/*
+ *
+ *  Copyright (C) 2019-2020, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmseg
+ *
+ *  Author:  Michael Onken
+ *
+ *  Purpose: Test for creating, writing and reading Segmentation objects
+ *
+ */
+
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
+
+#include "dcmtk/dcmseg/segdoc.h"
+#include "dcmtk/dcmseg/segment.h"
+#include "dcmtk/ofstd/oftest.h"
+
+#include "dcmtk/dcmfg/fgfracon.h"
+#include "dcmtk/dcmfg/fgpixmsr.h"
+#include "dcmtk/dcmfg/fgplanor.h"
+#include "dcmtk/dcmfg/fgplanpo.h"
+#include "dcmtk/dcmfg/fgseg.h"
+#include "dcmtk/dcmiod/iodmacro.h"
+#include "dcmtk/ofstd/ofmem.h"
+#include "dcmtk/ofstd/ofstrutl.h"
+#include "dcmtk/ofstd/oftempf.h"
+#include "dcmtk/ofstd/oftest.h"
+
+static const Uint8 NUM_ROWS             = 10;
+static const Uint8 NUM_COLS             = 10;
+static const Uint8 NUM_FRAMES           = 10;
+static const Uint8 NUM_PIXELS_PER_FRAME = NUM_COLS * NUM_ROWS;
+
+static OFString EXPECTED_DUMP;
+
+static void prepareExpectedDump();
+static DcmSegmentation* create();
+static void setGenericValues(DcmSegmentation* seg);
+static void addSharedFGs(DcmSegmentation* seg);
+static void addFrames(DcmSegmentation* seg);
+static void addDimensions(DcmSegmentation* seg);
+static OFString write(DcmSegmentation* seg, DcmDataset& ds);
+static void writeAndCheckConcatenation(DcmSegmentation* seg, OFList<OFFilename>& concats);
+static void checkCreatedObject(const OFString& ds_dump);
+static void loadAndCheckConcatenation(const OFList<OFFilename>& concats);
+static void checkConcatenationInstance(size_t numInstance, DcmSegmentation* srcInstance, DcmDataset* concatInstance);
+
+OFTEST(dcmseg_roundtrip)
+{
+    // Make sure data dictionary is loaded
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
+    // Creation
+    DcmSegmentation* seg = create();
+    setGenericValues(seg);
+    addSharedFGs(seg);
+    addFrames(seg);
+    addDimensions(seg);
+
+    // Write to dataset and compare its dump with expected result
+    DcmFileFormat dcmff;
+    DcmDataset* ds = dcmff.getDataset();
+    prepareExpectedDump();
+    OFString dset_dump = write(seg, *ds);
+    checkCreatedObject(dset_dump);
+
+    // Save to disk, and re-load to test import
+    OFTempFile tf;
+    OFString temp_fn = tf.getFilename();
+    OFCHECK(!temp_fn.empty());
+    OFCHECK(seg->saveFile(temp_fn.c_str(), EXS_LittleEndianExplicit).good());
+
+    // Read object from dataset into DcmSegmentation object, write again to dataset and
+    // check whether object after writing is identical to object after writing.
+    // the same expected result
+    delete seg;
+    seg = NULL;
+    DcmSegmentation::loadFile(temp_fn, seg).good();
+    OFCHECK(seg != OFnullptr);
+    if (seg)
+    {
+        dset_dump = write(seg, *ds);
+        checkCreatedObject(dset_dump);
+    }
+
+    // Check writing the object to a concatenation
+    OFList<OFFilename> concats;
+    writeAndCheckConcatenation(seg, concats);
+
+    // Re-load object from concatenation
+    loadAndCheckConcatenation(concats);
+
+    OFListIterator(OFFilename) delFile = concats.begin();
+    while (delFile != concats.end())
+    {
+        OFStandard::deleteFile(*delFile);
+        delFile++;
+    }
+    delete seg;
+}
+
+static DcmSegmentation* create()
+{
+    IODGeneralEquipmentModule::EquipmentInfo eq("Open Connections", "OC CT", "4711", "0.1");
+    ContentIdentificationMacro ci("1", "LABEL", "DESCRIPTION", "Doe^John");
+    DcmSegmentation* seg = NULL;
+    OFCondition result;
+    DcmSegmentation::createFractionalSegmentation(seg, NUM_ROWS, NUM_COLS, DcmSegTypes::SFT_OCCUPANCY, 255, eq, ci);
+    OFCHECK(result.good());
+    OFCHECK(seg != OFnullptr);
+    return seg;
+}
+
+static void setGenericValues(DcmSegmentation* seg)
+{
+    if (!seg)
+        return;
+    OFCHECK(seg->getPatient().setPatientName("Bond^James").good());
+    OFCHECK(seg->getPatient().setPatientID("007").good());
+    OFCHECK(seg->getPatient().setPatientBirthDate("19771007").good());
+    OFCHECK(seg->getStudy().setStudyDate("20190801").good());
+    OFCHECK(seg->getStudy().setStudyTime("120000").good());
+    OFCHECK(seg->getStudy().setStudyID("1").good());
+    OFCHECK(seg->getPatientStudy().setPatientAge("040Y").good());
+    OFCHECK(seg->getSeries().setSeriesDescription("Test Description").good());
+    OFCHECK(seg->getSeries().setSeriesNumber("1").good());
+    OFCHECK(seg->getSeries().setPatientPosition("HFS").good());
+
+    // Those values are usually computed automatically. UIDS are generated and date/times are set to current values.
+    // But in order to compare the "old" dump with the freshly created image attributes, we set some values manually,
+    // so that they are not overwritten with new, automatically created values later.
+    OFCHECK(seg->getStudy().setStudyInstanceUID("1.2.276.0.7230010.3.1.2.8323329.14863.1565940357.864811").good());
+    OFCHECK(seg->getFrameOfReference().setFrameOfReferenceUID("2.25.30853397773651184949181049330553108086").good());
+    OFCHECK(seg->getSeries().setSeriesInstanceUID("1.2.276.0.7230010.3.1.3.8323329.14863.1565940357.864812").good());
+    OFCHECK(seg->getSOPCommon().setSOPInstanceUID("1.2.276.0.7230010.3.1.4.8323329.14863.1565940357.864813").good());
+    OFCHECK(seg->getGeneralImage().setContentDate("20190927").good());
+    OFCHECK(seg->getGeneralImage().setContentTime("153857").good());
+}
+
+static void addSharedFGs(DcmSegmentation* seg)
+{
+    if (!seg)
+        return;
+
+    FGPixelMeasures meas;
+    OFCHECK(meas.setPixelSpacing("0.1\\0.1").good());
+    OFCHECK(meas.setSliceThickness("1.0").good());
+    OFCHECK(meas.setSpacingBetweenSlices("0.05").good());
+
+    FGPlanePosPatient planpo;
+    OFCHECK(planpo.setImagePositionPatient("0.0", "0.0", "0.0").good());
+
+    FGPlaneOrientationPatient planor;
+    OFCHECK(planor.setImageOrientationPatient("1.0", "0.0", "0.0", "0.0", "1.0", "0.0").good());
+
+    OFCHECK(seg->addForAllFrames(meas).good());
+    OFCHECK(seg->addForAllFrames(planpo).good());
+    OFCHECK(seg->addForAllFrames(planor).good());
+}
+
+static void addFrames(DcmSegmentation* seg)
+{
+    if (!seg)
+        return;
+
+    FGSegmentation* fg_seg = new FGSegmentation();
+    FGFrameContent* fg     = new FGFrameContent();
+    OFCHECK(fg && fg_seg);
+    fg->setStackID("1");
+    if (fg)
+    {
+        for (Uint16 frameNo = 1; frameNo <= NUM_FRAMES; frameNo++)
+        {
+            DcmSegment* segment = NULL;
+            CodeSequenceMacro category("85756007", "SCT", "Tissue");
+            CodeSequenceMacro propType("51114001", "SCT", "Artery");
+            OFCHECK(DcmSegment::create(segment, "SEGLABEL", category, propType, DcmSegTypes::SAT_AUTOMATIC, "OC_DUMMY")
+                        .good());
+            OFCHECK(segment != OFnullptr);
+            OFCHECK(seg->addSegment(segment, frameNo).good());
+
+            OFCHECK(fg->setFrameAcquisitionNumber(frameNo).good());
+            OFCHECK(fg->setFrameReferenceDateTime("20190816092557").good());
+            OFCHECK(fg->setFrameAcquisitionDateTime("20190816092557").good());
+            OFCHECK(fg->setFrameAcquisitionDuration(0.001).good());
+            OFCHECK(fg->setInStackPositionNumber(frameNo).good());
+            OFCHECK(fg->setDimensionIndexValues(1, 0).good());
+            OFCHECK(fg->setDimensionIndexValues(frameNo, 1).good());
+            OFVector<FGBase*> groups;
+            groups.push_back(fg);
+
+            Uint8* data = new Uint8[NUM_PIXELS_PER_FRAME];
+            for (Uint8 i = 0; i < NUM_PIXELS_PER_FRAME; ++i)
+            {
+                data[i] = i;
+            }
+            OFCHECK(fg_seg->setReferencedSegmentNumber(frameNo).good());
+            OFVector<FGBase*> perFrameFGs;
+            perFrameFGs.push_back(fg);
+            perFrameFGs.push_back(fg_seg);
+            OFCHECK(seg->addFrame(data, frameNo, perFrameFGs).good());
+            delete[] data;
+        }
+    }
+    delete fg;
+    delete fg_seg;
+}
+
+static void addDimensions(DcmSegmentation* seg)
+{
+    if (!seg)
+        return;
+    IODMultiframeDimensionModule& dims = seg->getDimensions();
+    OFCHECK(dims.addDimensionIndex(
+                    DCM_StackID, "2.25.30855560781715986879861690673941231222", DCM_FrameContentSequence, "STACK_DIM")
+                .good());
+    OFCHECK(dims.addDimensionIndex(DCM_InStackPositionNumber,
+                                   "2.25.30855560781715986879861690673941231222",
+                                   DCM_FrameContentSequence,
+                                   "STACK_DIM")
+                .good());
+    OFunique_ptr<IODMultiframeDimensionModule::DimensionOrganizationItem> org(
+        new IODMultiframeDimensionModule::DimensionOrganizationItem);
+    if (org)
+    {
+        org->setDimensionOrganizationUID("2.25.30855560781715986879861690673941231222");
+        dims.getDimensionOrganizationSequence().push_back(org.release());
+    }
+}
+
+static OFString write(DcmSegmentation* seg, DcmDataset& ds)
+{
+    OFCondition result = seg->writeDataset(ds);
+    OFCHECK(result.good());
+    // Make dump and return it
+    OFStringStream sstream;
+    ds.print(sstream);
+    OFSTRINGSTREAM_GETOFSTRING(sstream, dump);
+
+    return dump;
+}
+
+static void writeAndCheckConcatenation(DcmSegmentation* seg, OFList<OFFilename>& concats)
+{
+    ConcatenationCreator cc;
+    cc.setCfgFramesPerInstance(1);
+    OFCHECK(seg->writeConcatenation(cc).good());
+    size_t numInstances = cc.getNumInstances();
+    OFCHECK(numInstances == NUM_FRAMES);
+    OFCondition result;
+    for (size_t n = 0; n < numInstances; n++)
+    {
+        OFStringStream s;
+        s << "concat_" << n << "_";
+        OFTempFile tf(O_RDWR, "", s.str().c_str(), ".dcm");
+        result = cc.writeNextInstance(tf.getFilename());
+        OFCHECK(result.good());
+        if (result.good())
+        {
+            DcmFileFormat concat;
+            result = concat.loadFile(tf.getFilename());
+            OFCHECK(result.good());
+            checkConcatenationInstance(n, seg, concat.getDataset());
+            concats.push_back(tf.getFilename());
+            tf.stealFile();
+        }
+    }
+}
+
+static void checkConcatenationInstance(size_t numInstance, DcmSegmentation* srcInstance, DcmDataset* concatInstance)
+{
+    DcmSegmentation* concat = NULL;
+    OFCHECK(DcmSegmentation::loadDataset(*concatInstance, concat).good());
+    size_t numFrames;
+    numFrames = concat->getNumberOfFrames();
+    OFCHECK(numFrames == 1);
+    size_t numSegs = concat->getNumberOfSegments();
+    OFCHECK(numSegs == NUM_FRAMES);
+    IODMultiFrameFGModule::ConcatenationInfo& ci = concat->getConcatenationInfo();
+    OFString val;
+    OFCHECK(ci.getConcatenationUID(val).good());
+    OFCHECK(DcmUniqueIdentifier::checkStringValue(val, "1").good());
+    Uint32 frameOffsetNo = 0;
+    OFCHECK(ci.getConcatenationFrameOffsetNumber(frameOffsetNo).good());
+    OFCHECK(frameOffsetNo == numInstance);
+    Uint16 inConcatNo = 0;
+    OFCHECK(ci.getInConcatenationNumber(inConcatNo).good());
+    OFCHECK(inConcatNo == numInstance + 1);
+    Uint16 concatTotalNo = 0;
+    OFCHECK(ci.getInConcatenationTotalNumber(concatTotalNo).good());
+    OFCHECK(concatTotalNo == NUM_FRAMES);
+
+    OFString srcUID;
+    OFCHECK(ci.getSOPInstanceUIDOfConcatenationSource(srcUID).good());
+    OFCHECK(srcInstance->getSOPCommon().getSOPInstanceUID(val).good());
+    OFCHECK(srcUID == val);
+
+    OFCHECK(concat->getSOPCommon().getSOPInstanceUID(val).good());
+    OFCHECK(srcUID != val);
+
+    FunctionalGroups::const_iterator srcShared = srcInstance->getFunctionalGroups().getShared()->begin();
+    FunctionalGroups::const_iterator cShared   = concat->getFunctionalGroups().getShared()->begin();
+    size_t numShared                           = 0;
+    do
+    {
+        OFCHECK(srcShared->second->compare(*cShared->second) == 0);
+        srcShared++;
+        cShared++;
+        numShared++;
+    } while ((srcShared != srcInstance->getFunctionalGroups().getShared()->end())
+             && (cShared != concat->getFunctionalGroups().getShared()->end()));
+    OFCHECK((srcShared == srcInstance->getFunctionalGroups().getShared()->end())
+            && (cShared == concat->getFunctionalGroups().getShared()->end()));
+    DcmSequenceOfItems* cPerFrame = NULL;
+    OFCHECK(concatInstance->findAndGetSequence(DCM_PerFrameFunctionalGroupsSequence, cPerFrame).good());
+    OFCHECK(cPerFrame->card() == 1);
+
+    OFBool perFrame = OFFalse;
+    FGBase* fg      = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_FRAMECONTENT, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFTrue);
+
+    fg = NULL;
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_SEGMENTATION, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFTrue);
+
+    fg = NULL;
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_PIXELMEASURES, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = NULL;
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_PLANEPOSPATIENT, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    fg = NULL;
+    fg = concat->getFunctionalGroups().get(0, DcmFGTypes::EFG_PLANEORIENTPATIENT, perFrame);
+    OFCHECK(fg != NULL);
+    OFCHECK(perFrame == OFFalse);
+
+    const DcmIODTypes::Frame* frame = concat->getFrame(0);
+    OFCHECK(frame != OFnullptr);
+    OFCHECK(frame->pixData != OFnullptr);
+    OFCHECK(OFstatic_cast(Uint8, frame->length) == NUM_PIXELS_PER_FRAME);
+    for (size_t pix = 0; pix < frame->length; pix++)
+    {
+        OFCHECK(frame->pixData[pix] == pix);
+    }
+    delete concat;
+}
+
+static void loadAndCheckConcatenation(const OFList<OFFilename>& concats)
+{
+    ConcatenationLoader cl;
+    OFCondition result = cl.scan(concats);
+    OFCHECK(result.good());
+    if (result.good())
+    {
+        ConcatenationLoader::TScanResult results = cl.getInfo();
+        OFCHECK(results.size() == 1);
+        if (results.size() != 1)
+            return;
+        DcmSegmentation* seg = NULL;
+        result               = DcmSegmentation::loadConcatenation(cl, results.begin()->first, seg);
+
+        OFCHECK(result.good());
+        if (result.good())
+        {
+            OFStringStream s;
+            DcmDataset dset;
+            OFString sop;
+            result = seg->writeDataset(dset);
+
+            // Patch date and time so that it fits the prepared dump
+            OFCHECK(dset.putAndInsertOFStringArray(DCM_ContentDate, "20190927").good());
+            OFCHECK(dset.putAndInsertOFStringArray(DCM_ContentTime, "153857").good());
+
+            dset.print(s);
+            OFCHECK(result.good());
+            if (result.good())
+            {
+                checkCreatedObject(s.str().c_str());
+            }
+            delete seg;
+        }
+    }
+}
+
+static void prepareExpectedDump()
+{
+    EXPECTED_DUMP = "\n";
+    EXPECTED_DUMP += "# Dicom-Data-Set\n";
+    EXPECTED_DUMP += "# Used TransferSyntax: Little Endian Explicit\n";
+    EXPECTED_DUMP += "(0008,0008) CS [DERIVED\\PRIMARY]                        #  16, 2 ImageType\n";
+    EXPECTED_DUMP += "(0008,0016) UI =SegmentationStorage                     #  28, 1 SOPClassUID\n";
+    EXPECTED_DUMP
+        += "(0008,0018) UI [1.2.276.0.7230010.3.1.4.8323329.14863.1565940357.864813] #  56, 1 SOPInstanceUID\n";
+    EXPECTED_DUMP += "(0008,0020) DA [20190801]                               #   8, 1 StudyDate\n";
+    EXPECTED_DUMP += "(0008,0023) DA [20190927]                               #   8, 1 ContentDate\n";
+    EXPECTED_DUMP += "(0008,0030) TM [120000]                                 #   6, 1 StudyTime\n";
+    EXPECTED_DUMP += "(0008,0033) TM [153857]                                 #   6, 1 ContentTime\n";
+    EXPECTED_DUMP += "(0008,0050) SH (no value available)                     #   0, 0 AccessionNumber\n";
+    EXPECTED_DUMP += "(0008,0060) CS [SEG]                                    #   4, 1 Modality\n";
+    EXPECTED_DUMP += "(0008,0070) LO [Open Connections]                       #  16, 1 Manufacturer\n";
+    EXPECTED_DUMP += "(0008,0090) PN (no value available)                     #   0, 0 ReferringPhysicianName\n";
+    EXPECTED_DUMP += "(0008,103e) LO [Test Description]                       #  16, 1 SeriesDescription\n";
+    EXPECTED_DUMP += "(0008,1090) LO [OC CT]                                  #   6, 1 ManufacturerModelName\n";
+    EXPECTED_DUMP += "(0010,0010) PN [Bond^James]                             #  10, 1 PatientName\n";
+    EXPECTED_DUMP += "(0010,0020) LO [007]                                    #   4, 1 PatientID\n";
+    EXPECTED_DUMP += "(0010,0030) DA [19771007]                               #   8, 1 PatientBirthDate\n";
+    EXPECTED_DUMP += "(0010,0040) CS (no value available)                     #   0, 0 PatientSex\n";
+    EXPECTED_DUMP += "(0010,1010) AS [040Y]                                   #   4, 1 PatientAge\n";
+    EXPECTED_DUMP += "(0018,1000) LO [4711]                                   #   4, 1 DeviceSerialNumber\n";
+    EXPECTED_DUMP += "(0018,1020) LO [0.1]                                    #   4, 1 SoftwareVersions\n";
+    EXPECTED_DUMP += "(0018,5100) CS [HFS]                                    #   4, 1 PatientPosition\n";
+    EXPECTED_DUMP
+        += "(0020,000d) UI [1.2.276.0.7230010.3.1.2.8323329.14863.1565940357.864811] #  56, 1 StudyInstanceUID\n";
+    EXPECTED_DUMP
+        += "(0020,000e) UI [1.2.276.0.7230010.3.1.3.8323329.14863.1565940357.864812] #  56, 1 SeriesInstanceUID\n";
+    EXPECTED_DUMP += "(0020,0010) SH [1]                                      #   2, 1 StudyID\n";
+    EXPECTED_DUMP += "(0020,0011) IS [1]                                      #   2, 1 SeriesNumber\n";
+    EXPECTED_DUMP += "(0020,0013) IS [1]                                      #   2, 1 InstanceNumber\n";
+    EXPECTED_DUMP += "(0020,0052) UI [2.25.30853397773651184949181049330553108086] #  44, 1 FrameOfReferenceUID\n";
+    EXPECTED_DUMP += "(0020,1040) LO (no value available)                     #   0, 0 PositionReferenceIndicator\n";
+    EXPECTED_DUMP += "(0020,9221) SQ (Sequence with explicit length #=1)      #   0, 1 DimensionOrganizationSequence\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "    (0020,9164) UI [2.25.30855560781715986879861690673941231222] #  44, 1 DimensionOrganizationUID\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "(0020,9222) SQ (Sequence with explicit length #=2)      #   0, 1 DimensionIndexSequence\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=4)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "    (0020,9164) UI [2.25.30855560781715986879861690673941231222] #  44, 1 DimensionOrganizationUID\n";
+    EXPECTED_DUMP += "    (0020,9165) AT (0020,9056)                              #   4, 1 DimensionIndexPointer\n";
+    EXPECTED_DUMP += "    (0020,9167) AT (0020,9111)                              #   4, 1 FunctionalGroupPointer\n";
+    EXPECTED_DUMP += "    (0020,9421) LO [STACK_DIM]                              #  10, 1 DimensionDescriptionLabel\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=4)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "    (0020,9164) UI [2.25.30855560781715986879861690673941231222] #  44, 1 DimensionOrganizationUID\n";
+    EXPECTED_DUMP += "    (0020,9165) AT (0020,9057)                              #   4, 1 DimensionIndexPointer\n";
+    EXPECTED_DUMP += "    (0020,9167) AT (0020,9111)                              #   4, 1 FunctionalGroupPointer\n";
+    EXPECTED_DUMP += "    (0020,9421) LO [STACK_DIM]                              #  10, 1 DimensionDescriptionLabel\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "(0028,0002) US 1                                        #   2, 1 SamplesPerPixel\n";
+    EXPECTED_DUMP += "(0028,0004) CS [MONOCHROME2]                            #  12, 1 PhotometricInterpretation\n";
+    EXPECTED_DUMP += "(0028,0008) IS [10]                                     #   2, 1 NumberOfFrames\n";
+    EXPECTED_DUMP += "(0028,0010) US 10                                       #   2, 1 Rows\n";
+    EXPECTED_DUMP += "(0028,0011) US 10                                       #   2, 1 Columns\n";
+    EXPECTED_DUMP += "(0028,0100) US 8                                        #   2, 1 BitsAllocated\n";
+    EXPECTED_DUMP += "(0028,0101) US 8                                        #   2, 1 BitsStored\n";
+    EXPECTED_DUMP += "(0028,0102) US 7                                        #   2, 1 HighBit\n";
+    EXPECTED_DUMP += "(0028,0103) US 0                                        #   2, 1 PixelRepresentation\n";
+    EXPECTED_DUMP += "(0028,2110) CS [00]                                     #   2, 1 LossyImageCompression\n";
+    EXPECTED_DUMP += "(0062,0001) CS [FRACTIONAL]                             #  10, 1 SegmentationType\n";
+    EXPECTED_DUMP += "(0062,0002) SQ (Sequence with explicit length #=10)     #   0, 1 SegmentSequence\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=6)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0062,0003) SQ (Sequence with explicit length #=1)      #   0, 1 "
+                     "SegmentedPropertyCategoryCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [85756007]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Tissue]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0062,0004) US 1                                        #   2, 1 SegmentNumber\n";
+    EXPECTED_DUMP += "    (0062,0005) LO [SEGLABEL]                               #   8, 1 SegmentLabel\n";
+    EXPECTED_DUMP += "    (0062,0008) CS [AUTOMATIC]                              #  10, 1 SegmentAlgorithmType\n";
+    EXPECTED_DUMP += "    (0062,0009) LO [OC_DUMMY]                               #   8, 1 SegmentAlgorithmName\n";
+    EXPECTED_DUMP
+        += "    (0062,000f) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentedPropertyTypeCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [51114001]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Artery]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=6)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0062,0003) SQ (Sequence with explicit length #=1)      #   0, 1 "
+                     "SegmentedPropertyCategoryCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [85756007]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Tissue]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0062,0004) US 2                                        #   2, 1 SegmentNumber\n";
+    EXPECTED_DUMP += "    (0062,0005) LO [SEGLABEL]                               #   8, 1 SegmentLabel\n";
+    EXPECTED_DUMP += "    (0062,0008) CS [AUTOMATIC]                              #  10, 1 SegmentAlgorithmType\n";
+    EXPECTED_DUMP += "    (0062,0009) LO [OC_DUMMY]                               #   8, 1 SegmentAlgorithmName\n";
+    EXPECTED_DUMP
+        += "    (0062,000f) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentedPropertyTypeCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [51114001]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Artery]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=6)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0062,0003) SQ (Sequence with explicit length #=1)      #   0, 1 "
+                     "SegmentedPropertyCategoryCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [85756007]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Tissue]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0062,0004) US 3                                        #   2, 1 SegmentNumber\n";
+    EXPECTED_DUMP += "    (0062,0005) LO [SEGLABEL]                               #   8, 1 SegmentLabel\n";
+    EXPECTED_DUMP += "    (0062,0008) CS [AUTOMATIC]                              #  10, 1 SegmentAlgorithmType\n";
+    EXPECTED_DUMP += "    (0062,0009) LO [OC_DUMMY]                               #   8, 1 SegmentAlgorithmName\n";
+    EXPECTED_DUMP
+        += "    (0062,000f) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentedPropertyTypeCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [51114001]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Artery]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=6)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0062,0003) SQ (Sequence with explicit length #=1)      #   0, 1 "
+                     "SegmentedPropertyCategoryCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [85756007]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Tissue]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0062,0004) US 4                                        #   2, 1 SegmentNumber\n";
+    EXPECTED_DUMP += "    (0062,0005) LO [SEGLABEL]                               #   8, 1 SegmentLabel\n";
+    EXPECTED_DUMP += "    (0062,0008) CS [AUTOMATIC]                              #  10, 1 SegmentAlgorithmType\n";
+    EXPECTED_DUMP += "    (0062,0009) LO [OC_DUMMY]                               #   8, 1 SegmentAlgorithmName\n";
+    EXPECTED_DUMP
+        += "    (0062,000f) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentedPropertyTypeCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [51114001]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Artery]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=6)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0062,0003) SQ (Sequence with explicit length #=1)      #   0, 1 "
+                     "SegmentedPropertyCategoryCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [85756007]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Tissue]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0062,0004) US 5                                        #   2, 1 SegmentNumber\n";
+    EXPECTED_DUMP += "    (0062,0005) LO [SEGLABEL]                               #   8, 1 SegmentLabel\n";
+    EXPECTED_DUMP += "    (0062,0008) CS [AUTOMATIC]                              #  10, 1 SegmentAlgorithmType\n";
+    EXPECTED_DUMP += "    (0062,0009) LO [OC_DUMMY]                               #   8, 1 SegmentAlgorithmName\n";
+    EXPECTED_DUMP
+        += "    (0062,000f) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentedPropertyTypeCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [51114001]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Artery]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=6)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0062,0003) SQ (Sequence with explicit length #=1)      #   0, 1 "
+                     "SegmentedPropertyCategoryCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [85756007]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Tissue]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0062,0004) US 6                                        #   2, 1 SegmentNumber\n";
+    EXPECTED_DUMP += "    (0062,0005) LO [SEGLABEL]                               #   8, 1 SegmentLabel\n";
+    EXPECTED_DUMP += "    (0062,0008) CS [AUTOMATIC]                              #  10, 1 SegmentAlgorithmType\n";
+    EXPECTED_DUMP += "    (0062,0009) LO [OC_DUMMY]                               #   8, 1 SegmentAlgorithmName\n";
+    EXPECTED_DUMP
+        += "    (0062,000f) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentedPropertyTypeCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [51114001]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Artery]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=6)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0062,0003) SQ (Sequence with explicit length #=1)      #   0, 1 "
+                     "SegmentedPropertyCategoryCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [85756007]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Tissue]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0062,0004) US 7                                        #   2, 1 SegmentNumber\n";
+    EXPECTED_DUMP += "    (0062,0005) LO [SEGLABEL]                               #   8, 1 SegmentLabel\n";
+    EXPECTED_DUMP += "    (0062,0008) CS [AUTOMATIC]                              #  10, 1 SegmentAlgorithmType\n";
+    EXPECTED_DUMP += "    (0062,0009) LO [OC_DUMMY]                               #   8, 1 SegmentAlgorithmName\n";
+    EXPECTED_DUMP
+        += "    (0062,000f) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentedPropertyTypeCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [51114001]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Artery]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=6)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0062,0003) SQ (Sequence with explicit length #=1)      #   0, 1 "
+                     "SegmentedPropertyCategoryCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [85756007]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Tissue]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0062,0004) US 8                                        #   2, 1 SegmentNumber\n";
+    EXPECTED_DUMP += "    (0062,0005) LO [SEGLABEL]                               #   8, 1 SegmentLabel\n";
+    EXPECTED_DUMP += "    (0062,0008) CS [AUTOMATIC]                              #  10, 1 SegmentAlgorithmType\n";
+    EXPECTED_DUMP += "    (0062,0009) LO [OC_DUMMY]                               #   8, 1 SegmentAlgorithmName\n";
+    EXPECTED_DUMP
+        += "    (0062,000f) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentedPropertyTypeCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [51114001]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Artery]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=6)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0062,0003) SQ (Sequence with explicit length #=1)      #   0, 1 "
+                     "SegmentedPropertyCategoryCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [85756007]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Tissue]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0062,0004) US 9                                        #   2, 1 SegmentNumber\n";
+    EXPECTED_DUMP += "    (0062,0005) LO [SEGLABEL]                               #   8, 1 SegmentLabel\n";
+    EXPECTED_DUMP += "    (0062,0008) CS [AUTOMATIC]                              #  10, 1 SegmentAlgorithmType\n";
+    EXPECTED_DUMP += "    (0062,0009) LO [OC_DUMMY]                               #   8, 1 SegmentAlgorithmName\n";
+    EXPECTED_DUMP
+        += "    (0062,000f) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentedPropertyTypeCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [51114001]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Artery]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=6)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0062,0003) SQ (Sequence with explicit length #=1)      #   0, 1 "
+                     "SegmentedPropertyCategoryCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [85756007]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Tissue]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0062,0004) US 10                                       #   2, 1 SegmentNumber\n";
+    EXPECTED_DUMP += "    (0062,0005) LO [SEGLABEL]                               #   8, 1 SegmentLabel\n";
+    EXPECTED_DUMP += "    (0062,0008) CS [AUTOMATIC]                              #  10, 1 SegmentAlgorithmType\n";
+    EXPECTED_DUMP += "    (0062,0009) LO [OC_DUMMY]                               #   8, 1 SegmentAlgorithmName\n";
+    EXPECTED_DUMP
+        += "    (0062,000f) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentedPropertyTypeCodeSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0008,0100) SH [51114001]                               #   8, 1 CodeValue\n";
+    EXPECTED_DUMP
+        += "        (0008,0102) SH [SCT]                                    #   4, 1 CodingSchemeDesignator\n";
+    EXPECTED_DUMP += "        (0008,0104) LO [Artery]                                 #   6, 1 CodeMeaning\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "(0062,000e) US 255                                      #   2, 1 MaximumFractionalValue\n";
+    EXPECTED_DUMP += "(0062,0010) CS [OCCUPANCY]                              #  10, 1 SegmentationFractionalType\n";
+    EXPECTED_DUMP += "(0070,0080) CS [LABEL]                                  #   6, 1 ContentLabel\n";
+    EXPECTED_DUMP += "(0070,0081) LO [DESCRIPTION]                            #  12, 1 ContentDescription\n";
+    EXPECTED_DUMP += "(0070,0084) PN [Doe^John]                               #   8, 1 ContentCreatorName\n";
+    EXPECTED_DUMP
+        += "(5200,9229) SQ (Sequence with explicit length #=1)      #   0, 1 SharedFunctionalGroupsSequence\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0020,9113) SQ (Sequence with explicit length #=1)      #   0, 1 PlanePositionSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0020,0032) DS [0.0\\0.0\\0.0]                            #  12, 3 ImagePositionPatient\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0020,9116) SQ (Sequence with explicit length #=1)      #   0, 1 PlaneOrientationSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0020,0037) DS [1.0\\0.0\\0.0\\0.0\\1.0\\0.0]                #  24, 6 ImageOrientationPatient\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "    (0028,9110) SQ (Sequence with explicit length #=1)      #   0, 1 PixelMeasuresSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=3)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "        (0018,0050) DS [1.0]                                    #   4, 1 SliceThickness\n";
+    EXPECTED_DUMP += "        (0018,0088) DS [0.05]                                   #   4, 1 SpacingBetweenSlices\n";
+    EXPECTED_DUMP += "        (0028,0030) DS [0.1\\0.1]                                #   8, 2 PixelSpacing\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "(5200,9230) SQ (Sequence with explicit length #=10)     #   0, 1 PerFrameFunctionalGroupsSequence\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=2)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0020,9111) SQ (Sequence with explicit length #=1)      #   0, 1 FrameContentSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,9074) DT [20190816092557]                         #  14, 1 FrameAcquisitionDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9151) DT [20190816092557]                         #  14, 1 FrameReferenceDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9220) FD 0.001                                    #   8, 1 FrameAcquisitionDuration\n";
+    EXPECTED_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    EXPECTED_DUMP += "        (0020,9057) UL 1                                        #   4, 1 InStackPositionNumber\n";
+    EXPECTED_DUMP
+        += "        (0020,9156) US 1                                        #   2, 1 FrameAcquisitionNumber\n";
+    EXPECTED_DUMP += "        (0020,9157) UL 1\\1                                      #   8, 2 DimensionIndexValues\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "    (0062,000a) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentIdentificationSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0062,000b) US 1                                        #   2, 1 ReferencedSegmentNumber\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=2)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0020,9111) SQ (Sequence with explicit length #=1)      #   0, 1 FrameContentSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,9074) DT [20190816092557]                         #  14, 1 FrameAcquisitionDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9151) DT [20190816092557]                         #  14, 1 FrameReferenceDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9220) FD 0.001                                    #   8, 1 FrameAcquisitionDuration\n";
+    EXPECTED_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    EXPECTED_DUMP += "        (0020,9057) UL 2                                        #   4, 1 InStackPositionNumber\n";
+    EXPECTED_DUMP
+        += "        (0020,9156) US 2                                        #   2, 1 FrameAcquisitionNumber\n";
+    EXPECTED_DUMP += "        (0020,9157) UL 1\\2                                      #   8, 2 DimensionIndexValues\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "    (0062,000a) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentIdentificationSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0062,000b) US 2                                        #   2, 1 ReferencedSegmentNumber\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=2)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0020,9111) SQ (Sequence with explicit length #=1)      #   0, 1 FrameContentSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,9074) DT [20190816092557]                         #  14, 1 FrameAcquisitionDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9151) DT [20190816092557]                         #  14, 1 FrameReferenceDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9220) FD 0.001                                    #   8, 1 FrameAcquisitionDuration\n";
+    EXPECTED_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    EXPECTED_DUMP += "        (0020,9057) UL 3                                        #   4, 1 InStackPositionNumber\n";
+    EXPECTED_DUMP
+        += "        (0020,9156) US 3                                        #   2, 1 FrameAcquisitionNumber\n";
+    EXPECTED_DUMP += "        (0020,9157) UL 1\\3                                      #   8, 2 DimensionIndexValues\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "    (0062,000a) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentIdentificationSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0062,000b) US 3                                        #   2, 1 ReferencedSegmentNumber\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=2)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0020,9111) SQ (Sequence with explicit length #=1)      #   0, 1 FrameContentSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,9074) DT [20190816092557]                         #  14, 1 FrameAcquisitionDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9151) DT [20190816092557]                         #  14, 1 FrameReferenceDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9220) FD 0.001                                    #   8, 1 FrameAcquisitionDuration\n";
+    EXPECTED_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    EXPECTED_DUMP += "        (0020,9057) UL 4                                        #   4, 1 InStackPositionNumber\n";
+    EXPECTED_DUMP
+        += "        (0020,9156) US 4                                        #   2, 1 FrameAcquisitionNumber\n";
+    EXPECTED_DUMP += "        (0020,9157) UL 1\\4                                      #   8, 2 DimensionIndexValues\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "    (0062,000a) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentIdentificationSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0062,000b) US 4                                        #   2, 1 ReferencedSegmentNumber\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=2)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0020,9111) SQ (Sequence with explicit length #=1)      #   0, 1 FrameContentSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,9074) DT [20190816092557]                         #  14, 1 FrameAcquisitionDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9151) DT [20190816092557]                         #  14, 1 FrameReferenceDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9220) FD 0.001                                    #   8, 1 FrameAcquisitionDuration\n";
+    EXPECTED_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    EXPECTED_DUMP += "        (0020,9057) UL 5                                        #   4, 1 InStackPositionNumber\n";
+    EXPECTED_DUMP
+        += "        (0020,9156) US 5                                        #   2, 1 FrameAcquisitionNumber\n";
+    EXPECTED_DUMP += "        (0020,9157) UL 1\\5                                      #   8, 2 DimensionIndexValues\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "    (0062,000a) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentIdentificationSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0062,000b) US 5                                        #   2, 1 ReferencedSegmentNumber\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=2)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0020,9111) SQ (Sequence with explicit length #=1)      #   0, 1 FrameContentSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,9074) DT [20190816092557]                         #  14, 1 FrameAcquisitionDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9151) DT [20190816092557]                         #  14, 1 FrameReferenceDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9220) FD 0.001                                    #   8, 1 FrameAcquisitionDuration\n";
+    EXPECTED_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    EXPECTED_DUMP += "        (0020,9057) UL 6                                        #   4, 1 InStackPositionNumber\n";
+    EXPECTED_DUMP
+        += "        (0020,9156) US 6                                        #   2, 1 FrameAcquisitionNumber\n";
+    EXPECTED_DUMP += "        (0020,9157) UL 1\\6                                      #   8, 2 DimensionIndexValues\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "    (0062,000a) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentIdentificationSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0062,000b) US 6                                        #   2, 1 ReferencedSegmentNumber\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=2)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0020,9111) SQ (Sequence with explicit length #=1)      #   0, 1 FrameContentSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,9074) DT [20190816092557]                         #  14, 1 FrameAcquisitionDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9151) DT [20190816092557]                         #  14, 1 FrameReferenceDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9220) FD 0.001                                    #   8, 1 FrameAcquisitionDuration\n";
+    EXPECTED_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    EXPECTED_DUMP += "        (0020,9057) UL 7                                        #   4, 1 InStackPositionNumber\n";
+    EXPECTED_DUMP
+        += "        (0020,9156) US 7                                        #   2, 1 FrameAcquisitionNumber\n";
+    EXPECTED_DUMP += "        (0020,9157) UL 1\\7                                      #   8, 2 DimensionIndexValues\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "    (0062,000a) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentIdentificationSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0062,000b) US 7                                        #   2, 1 ReferencedSegmentNumber\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=2)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0020,9111) SQ (Sequence with explicit length #=1)      #   0, 1 FrameContentSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,9074) DT [20190816092557]                         #  14, 1 FrameAcquisitionDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9151) DT [20190816092557]                         #  14, 1 FrameReferenceDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9220) FD 0.001                                    #   8, 1 FrameAcquisitionDuration\n";
+    EXPECTED_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    EXPECTED_DUMP += "        (0020,9057) UL 8                                        #   4, 1 InStackPositionNumber\n";
+    EXPECTED_DUMP
+        += "        (0020,9156) US 8                                        #   2, 1 FrameAcquisitionNumber\n";
+    EXPECTED_DUMP += "        (0020,9157) UL 1\\8                                      #   8, 2 DimensionIndexValues\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "    (0062,000a) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentIdentificationSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0062,000b) US 8                                        #   2, 1 ReferencedSegmentNumber\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=2)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0020,9111) SQ (Sequence with explicit length #=1)      #   0, 1 FrameContentSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,9074) DT [20190816092557]                         #  14, 1 FrameAcquisitionDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9151) DT [20190816092557]                         #  14, 1 FrameReferenceDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9220) FD 0.001                                    #   8, 1 FrameAcquisitionDuration\n";
+    EXPECTED_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    EXPECTED_DUMP += "        (0020,9057) UL 9                                        #   4, 1 InStackPositionNumber\n";
+    EXPECTED_DUMP
+        += "        (0020,9156) US 9                                        #   2, 1 FrameAcquisitionNumber\n";
+    EXPECTED_DUMP += "        (0020,9157) UL 1\\9                                      #   8, 2 DimensionIndexValues\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "    (0062,000a) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentIdentificationSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0062,000b) US 9                                        #   2, 1 ReferencedSegmentNumber\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e000) na (Item with explicit length #=2)          #   0, 1 Item\n";
+    EXPECTED_DUMP += "    (0020,9111) SQ (Sequence with explicit length #=1)      #   0, 1 FrameContentSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=7)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0018,9074) DT [20190816092557]                         #  14, 1 FrameAcquisitionDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9151) DT [20190816092557]                         #  14, 1 FrameReferenceDateTime\n";
+    EXPECTED_DUMP
+        += "        (0018,9220) FD 0.001                                    #   8, 1 FrameAcquisitionDuration\n";
+    EXPECTED_DUMP += "        (0020,9056) SH [1]                                      #   2, 1 StackID\n";
+    EXPECTED_DUMP += "        (0020,9057) UL 10                                       #   4, 1 InStackPositionNumber\n";
+    EXPECTED_DUMP
+        += "        (0020,9156) US 10                                       #   2, 1 FrameAcquisitionNumber\n";
+    EXPECTED_DUMP += "        (0020,9157) UL 1\\10                                     #   8, 2 DimensionIndexValues\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "    (0062,000a) SQ (Sequence with explicit length #=1)      #   0, 1 SegmentIdentificationSequence\n";
+    EXPECTED_DUMP += "      (fffe,e000) na (Item with explicit length #=1)          #   0, 1 Item\n";
+    EXPECTED_DUMP
+        += "        (0062,000b) US 10                                       #   2, 1 ReferencedSegmentNumber\n";
+    EXPECTED_DUMP += "      (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "    (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP += "  (fffe,e00d) na (ItemDelimitationItem for re-encoding)   #   0, 0 ItemDelimitationItem\n";
+    EXPECTED_DUMP += "(fffe,e0dd) na (SequenceDelimitationItem for re-encod.) #   0, 0 SequenceDelimitationItem\n";
+    EXPECTED_DUMP
+        += "(7fe0,0010) OB "
+           "00\\01\\02\\03\\04\\05\\06\\07\\08\\09\\0a\\0b\\0c\\0d\\0e\\0f\\10\\11\\12\\13\\14\\15\\16\\17\\18\\19\\1a"
+           "\\1b\\1c\\1d\\1e\\1f\\20\\21\\22\\23\\24\\25\\26\\27\\28\\29\\2a\\2b\\2c\\2d\\2e\\2f\\30\\31\\32\\33\\34\\3"
+           "5\\36\\37\\38\\39\\3a\\3b\\3c\\3d\\3e\\3f\\40\\41\\42\\43\\44\\45\\46\\47\\48\\49\\4a\\4b\\4c\\4d\\4e\\4f\\"
+           "50\\51\\52\\53\\54\\55\\56\\57\\58\\59\\5a\\5b\\5c\\5d\\5e\\5f\\60\\61\\62\\63\\00\\01\\02\\03\\04\\05\\06"
+           "\\07\\08\\09\\0a\\0b\\0c\\0d\\0e\\0f\\10\\11\\12\\13\\14\\15\\16\\17\\18\\19\\1a\\1b\\1c\\1d\\1e\\1f\\20\\2"
+           "1\\22\\23\\24\\25\\26\\27\\28\\29\\2a\\2b\\2c\\2d\\2e\\2f\\30\\31\\32\\33\\34\\35\\36\\37\\38\\39\\3a\\3b\\"
+           "3c\\3d\\3e\\3f\\40\\41\\42\\43\\44\\45\\46\\47\\48\\49\\4a\\4b\\4c\\4d\\4e\\4f\\50\\51\\52\\53\\54\\55\\56"
+           "\\57\\58\\59\\5a\\5b\\5c\\5d\\5e\\5f\\60\\61\\62\\63\\00\\01\\02\\03\\04\\05\\06\\07\\08\\09\\0a\\0b\\0c\\0"
+           "d\\0e\\0f\\10\\11\\12\\13\\14\\15\\16\\17\\18\\19\\1a\\1b\\1c\\1d\\1e\\1f\\20\\21\\22\\23\\24\\25\\26\\27\\"
+           "28\\29\\2a\\2b\\2c\\2d\\2e\\2f\\30\\31\\32\\33\\34\\35\\36\\37\\38\\39\\3a\\3b\\3c\\3d\\3e\\3f\\40\\41\\42"
+           "\\43\\44\\45\\46\\47\\48\\49\\4a\\4b\\4c\\4d\\4e\\4f\\50\\51\\52\\53\\54\\55\\56\\57\\58\\59\\5a\\5b\\5c\\5"
+           "d\\5e\\5f\\60\\61\\62\\63\\00\\01\\02\\03\\04\\05\\06\\07\\08\\09\\0a\\0b\\0c\\0d\\0e\\0f\\10\\11\\12\\13\\"
+           "14\\15\\16\\17\\18\\19\\1a\\1b\\1c\\1d\\1e\\1f\\20\\21\\22\\23\\24\\25\\26\\27\\28\\29\\2a\\2b\\2c\\2d\\2e"
+           "\\2f\\30\\31\\32\\33\\34\\35\\36\\37\\38\\39\\3a\\3b\\3c\\3d\\3e\\3f\\40\\41\\42\\43\\44\\45\\46\\47\\48\\4"
+           "9\\4a\\4b\\4c\\4d\\4e\\4f\\50\\51\\52\\53\\54\\55\\56\\57\\58\\59\\5a\\5b\\5c\\5d\\5e\\5f\\60\\61\\62\\63\\"
+           "00\\01\\02\\03\\04\\05\\06\\07\\08\\09\\0a\\0b\\0c\\0d\\0e\\0f\\10\\11\\12\\13\\14\\15\\16\\17\\18\\19\\1a"
+           "\\1b\\1c\\1d\\1e\\1f\\20\\21\\22\\23\\24\\25\\26\\27\\28\\29\\2a\\2b\\2c\\2d\\2e\\2f\\30\\31\\32\\33\\34\\3"
+           "5\\36\\37\\38\\39\\3a\\3b\\3c\\3d\\3e\\3f\\40\\41\\42\\43\\44\\45\\46\\47\\48\\49\\4a\\4b\\4c\\4d\\4e\\4f\\"
+           "50\\51\\52\\53\\54\\55\\56\\57\\58\\59\\5a\\5b\\5c\\5d\\5e\\5f\\60\\61\\62\\63\\00\\01\\02\\03\\04\\05\\06"
+           "\\07\\08\\09\\0a\\0b\\0c\\0d\\0e\\0f\\10\\11\\12\\13\\14\\15\\16\\17\\18\\19\\1a\\1b\\1c\\1d\\1e\\1f\\20\\2"
+           "1\\22\\23\\24\\25\\26\\27\\28\\29\\2a\\2b\\2c\\2d\\2e\\2f\\30\\31\\32\\33\\34\\35\\36\\37\\38\\39\\3a\\3b\\"
+           "3c\\3d\\3e\\3f\\40\\41\\42\\43\\44\\45\\46\\47\\48\\49\\4a\\4b\\4c\\4d\\4e\\4f\\50\\51\\52\\53\\54\\55\\56"
+           "\\57\\58\\59\\5a\\5b\\5c\\5d\\5e\\5f\\60\\61\\62\\63\\00\\01\\02\\03\\04\\05\\06\\07\\08\\09\\0a\\0b\\0c\\0"
+           "d\\0e\\0f\\10\\11\\12\\13\\14\\15\\16\\17\\18\\19\\1a\\1b\\1c\\1d\\1e\\1f\\20\\21\\22\\23\\24\\25\\26\\27\\"
+           "28\\29\\2a\\2b\\2c\\2d\\2e\\2f\\30\\31\\32\\33\\34\\35\\36\\37\\38\\39\\3a\\3b\\3c\\3d\\3e\\3f\\40\\41\\42"
+           "\\43\\44\\45\\46\\47\\48\\49\\4a\\4b\\4c\\4d\\4e\\4f\\50\\51\\52\\53\\54\\55\\56\\57\\58\\59\\5a\\5b\\5c\\5"
+           "d\\5e\\5f\\60\\61\\62\\63\\00\\01\\02\\03\\04\\05\\06\\07\\08\\09\\0a\\0b\\0c\\0d\\0e\\0f\\10\\11\\12\\13\\"
+           "14\\15\\16\\17\\18\\19\\1a\\1b\\1c\\1d\\1e\\1f\\20\\21\\22\\23\\24\\25\\26\\27\\28\\29\\2a\\2b\\2c\\2d\\2e"
+           "\\2f\\30\\31\\32\\33\\34\\35\\36\\37\\38\\39\\3a\\3b\\3c\\3d\\3e\\3f\\40\\41\\42\\43\\44\\45\\46\\47\\48\\4"
+           "9\\4a\\4b\\4c\\4d\\4e\\4f\\50\\51\\52\\53\\54\\55\\56\\57\\58\\59\\5a\\5b\\5c\\5d\\5e\\5f\\60\\61\\62\\63\\"
+           "00\\01\\02\\03\\04\\05\\06\\07\\08\\09\\0a\\0b\\0c\\0d\\0e\\0f\\10\\11\\12\\13\\14\\15\\16\\17\\18\\19\\1a"
+           "\\1b\\1c\\1d\\1e\\1f\\20\\21\\22\\23\\24\\25\\26\\27\\28\\29\\2a\\2b\\2c\\2d\\2e\\2f\\30\\31\\32\\33\\34\\3"
+           "5\\36\\37\\38\\39\\3a\\3b\\3c\\3d\\3e\\3f\\40\\41\\42\\43\\44\\45\\46\\47\\48\\49\\4a\\4b\\4c\\4d\\4e\\4f\\"
+           "50\\51\\52\\53\\54\\55\\56\\57\\58\\59\\5a\\5b\\5c\\5d\\5e\\5f\\60\\61\\62\\63\\00\\01\\02\\03\\04\\05\\06"
+           "\\07\\08\\09\\0a\\0b\\0c\\0d\\0e\\0f\\10\\11\\12\\13\\14\\15\\16\\17\\18\\19\\1a\\1b\\1c\\1d\\1e\\1f\\20\\2"
+           "1\\22\\23\\24\\25\\26\\27\\28\\29\\2a\\2b\\2c\\2d\\2e\\2f\\30\\31\\32\\33\\34\\35\\36\\37\\38\\39\\3a\\3b\\"
+           "3c\\3d\\3e\\3f\\40\\41\\42\\43\\44\\45\\46\\47\\48\\49\\4a\\4b\\4c\\4d\\4e\\4f\\50\\51\\52\\53\\54\\55\\56"
+           "\\57\\58\\59\\5a\\5b\\5c\\5d\\5e\\5f\\60\\61\\62\\63 # 1000, 1 PixelData\n";
+}
+
+static void checkCreatedObject(const OFString& ds_dump)
+{
+    OFBool dump_ok = (ds_dump == EXPECTED_DUMP);
+    OFCHECK(dump_ok);
+    if (!dump_ok)
+    {
+        CERR << "Dump produced: " << OFendl << ds_dump << OFendl;
+        CERR << "------------------------------------" << OFendl;
+        CERR << "Dump expected: " << OFendl << EXPECTED_DUMP << OFendl;
+        CERR << "------------------------------------" << OFendl;
+    }
+}
index 4eaf1f8636478e65915b7938cca0c3ce3b03b747..36298f2ce4c2ed1d7da24d0d7c675b3e6de6c846 100644 (file)
  *
  */
 
+#include "dcmtk/config/osconfig.h" /* make sure OS specific configuration is included first */
 
-#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
-
-#include "dcmtk/ofstd/oftest.h"
+#include "dcmtk/dcmiod/iodutil.h"
 #include "dcmtk/dcmseg/segutils.h"
-
+#include "dcmtk/ofstd/oftest.h"
 
 #define bufLen 4
 
 static void resetBuf(Uint8* buf, const size_t length)
 {
-  if (length != bufLen) return;
-  buf[0] = 170; // 10101010
-  buf[1] = 204; // 11001100
-  buf[2] = 240; // 11110000
-  buf[3] = 15;  // 00001111
+    if (length != bufLen)
+        return;
+    buf[0] = 170; // 10101010
+    buf[1] = 204; // 11001100
+    buf[2] = 240; // 11110000
+    buf[3] = 15;  // 00001111
 }
 
 OFTEST(dcmseg_utils)
 {
-  // buf, always initialized/reset with: 10101010 11001100 11110000 00001111
-  Uint8 buf[bufLen];
-
-  resetBuf(buf, bufLen);
-  DcmSegUtils::alignFrameOnBitPosition(buf, 4, 2);
-  OFCHECK(buf[0] == 168); // 10101000
-  OFCHECK(buf[1] == 50);  // 00110010
-  OFCHECK(buf[2] == 195); // 11000011
-  OFCHECK(buf[3] == 63);  // 00111111
+    // buf, always initialized/reset with: 10101010 11001100 11110000 00001111
+    Uint8 buf[bufLen];
 
-  resetBuf(buf, bufLen);
-  DcmSegUtils::alignFrameOnByteBoundary(buf, 4, 2);
-  OFCHECK(buf[0] == 42);  // 00101010
-  OFCHECK(buf[1] == 51);  // 00110011
-  OFCHECK(buf[2] == 252); // 11111100
-  OFCHECK(buf[3] == 3);   // 00000011
+    resetBuf(buf, bufLen);
+    DcmSegUtils::alignFrameOnBitPosition(buf, 4, 2);
+    OFCHECK(buf[0] == 168); // 10101000
+    OFCHECK(buf[1] == 50);  // 00110010
+    OFCHECK(buf[2] == 195); // 11000011
+    OFCHECK(buf[3] == 63);  // 00111111
 
-  resetBuf(buf, bufLen);
-  DcmSegUtils::alignFrameOnBitPosition(buf, 4, 7);
-  OFCHECK(buf[0] == 0);
-  OFCHECK(buf[1] == 85);  // 01010101
-  OFCHECK(buf[2] == 102); // 01100110
-  OFCHECK(buf[3] == 248); // 11111000
+    resetBuf(buf, bufLen);
+    DcmSegUtils::alignFrameOnByteBoundary(buf, 4, 2);
+    OFCHECK(buf[0] == 42);  // 00101010
+    OFCHECK(buf[1] == 51);  // 00110011
+    OFCHECK(buf[2] == 252); // 11111100
+    OFCHECK(buf[3] == 3);   // 00000011
 
-  resetBuf(buf, bufLen);
-  DcmSegUtils::alignFrameOnByteBoundary(buf, 4, 7);
-  OFCHECK(buf[0] == 153); // 10011001
-  OFCHECK(buf[1] == 225); // 11100001
-  OFCHECK(buf[2] == 31);  // 00011111
-  OFCHECK(buf[3] == 0);
+    resetBuf(buf, bufLen);
+    DcmSegUtils::alignFrameOnBitPosition(buf, 4, 7);
+    OFCHECK(buf[0] == 0);
+    OFCHECK(buf[1] == 85);  // 01010101
+    OFCHECK(buf[2] == 102); // 01100110
+    OFCHECK(buf[3] == 248); // 11111000
 
+    resetBuf(buf, bufLen);
+    DcmSegUtils::alignFrameOnByteBoundary(buf, 4, 7);
+    OFCHECK(buf[0] == 153); // 10011001
+    OFCHECK(buf[1] == 225); // 11100001
+    OFCHECK(buf[2] == 31);  // 00011111
+    OFCHECK(buf[3] == 0);
 }
index a836795bae5c3c3b2afe0351eea7f0800bb19f47..7b05d8817974cafd59c370a9555d96d2c11fd531 100644 (file)
@@ -53,13 +53,17 @@ dcmsign.o: dcmsign.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../include/dcmtk/dcmsign/sipurpos.h ../include/dcmtk/dcmsign/dcsighlp.h \
  ../include/dcmtk/dcmsign/sinullpr.h ../include/dcmtk/dcmsign/sisprof.h \
  ../include/dcmtk/dcmsign/sibrsapr.h ../include/dcmtk/dcmsign/siautopr.h \
- ../include/dcmtk/dcmsign/sicreapr.h ../include/dcmtk/dcmsign/simac.h \
+ ../include/dcmtk/dcmsign/sicreapr.h ../include/dcmtk/dcmsign/sisrpr.h \
+ ../include/dcmtk/dcmsign/sisrvpr.h ../include/dcmtk/dcmsign/simac.h \
  ../include/dcmtk/dcmsign/simd5.h ../include/dcmtk/dcmsign/sisha1.h \
  ../include/dcmtk/dcmsign/sisha256.h ../include/dcmtk/dcmsign/sisha384.h \
  ../include/dcmtk/dcmsign/sisha512.h ../include/dcmtk/dcmsign/siripemd.h \
  ../include/dcmtk/dcmsign/siprivat.h ../include/dcmtk/dcmsign/sicert.h \
+ ../include/dcmtk/dcmsign/sitsfs.h ../include/dcmtk/dcmsign/sitstamp.h \
+ ../include/dcmtk/dcmsign/sicertvf.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
index 2097ce8d6db8eec6f919d62912a355e34d81ff8f..ce5317ab0e9a492657530a8348cfbf370581bf8b 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2000-2018, OFFIS e.V.
+ *  Copyright (C) 2000-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 static char rcsid[] = "$dcmtk: " OFFIS_CONSOLE_APPLICATION " v"
   OFFIS_DCMTK_VERSION " " OFFIS_DCMTK_RELEASEDATE " $";
 
-static OFLogger dcmsignLogger = OFLog::getLogger("dcmtk.apps." OFFIS_CONSOLE_APPLICATION);
-
 #define APPLICATION_ABSTRACT "Sign and Verify DICOM Files"
 
-
 #ifdef WITH_OPENSSL
 
 #include "dcmtk/dcmsign/dcsignat.h"
+#include "dcmtk/dcmsign/dcsighlp.h"
 #include "dcmtk/dcmsign/sinullpr.h"
 #include "dcmtk/dcmsign/sibrsapr.h"
 #include "dcmtk/dcmsign/siautopr.h"
 #include "dcmtk/dcmsign/sicreapr.h"
+#include "dcmtk/dcmsign/sisrpr.h"
+#include "dcmtk/dcmsign/sisrvpr.h"
 #include "dcmtk/dcmsign/simac.h"
 #include "dcmtk/dcmsign/simd5.h"
 #include "dcmtk/dcmsign/sisha1.h"
@@ -62,13 +62,17 @@ static OFLogger dcmsignLogger = OFLog::getLogger("dcmtk.apps." OFFIS_CONSOLE_APP
 #include "dcmtk/dcmsign/siripemd.h"
 #include "dcmtk/dcmsign/siprivat.h"
 #include "dcmtk/dcmsign/sicert.h"
+#include "dcmtk/dcmsign/sitsfs.h"
+#include "dcmtk/dcmsign/sicertvf.h"
+#include "dcmtk/dcmsign/siexit.h"
 #include "dcmtk/dcmdata/dctk.h"
 
-
 BEGIN_EXTERN_C
 #include <openssl/x509.h>
+#include <openssl/evp.h> /* for OPENSSL_NO_EC */
 END_EXTERN_C
 
+
 // ********************************************
 
 enum DcmSignOperation
@@ -76,616 +80,11 @@ enum DcmSignOperation
   DSO_verify,
   DSO_sign,
   DSO_signItem,
+  DSO_insertTimestamp,
   DSO_remove,
   DSO_removeAll
 };
 
-/* reads an attribute tag in the form "gggg,eeee" and adds it
- * to the given attribute tag list
- * @param c input string
- * @param tagList list to be added to
- * @return true if successful, false otherwise
- */
-static OFBool addTag(const char *c, DcmAttributeTag& tagList)
-{
-  OFBool result = OFFalse;
-  unsigned int group = 0xffff;
-  unsigned int elem = 0xffff;
-  if (sscanf(c, "%x,%x", &group, &elem ) != 2 )
-  {
-    /* it is a name */
-    const DcmDataDictionary& globalDataDict = dcmDataDict.rdlock();
-    const DcmDictEntry *dicent = globalDataDict.findEntry(c);
-    if (dicent)
-    {
-      if (EC_Normal == tagList.putTagVal(dicent->getKey(), tagList.getVM())) result = OFTrue;
-    }
-    dcmDataDict.rdunlock();
-  } else {
-    if (EC_Normal == tagList.putTagVal(DcmTagKey(group,elem), tagList.getVM())) result = OFTrue;
-  }
-  return result;
-}
-
-/* scans a token from the given string and returns it. Ignores leading whitespace.
- * @param c string to parse
- * @param pos position within string, modified after successful scan
- * @param key tag key returned in this parameter if return value is "tag key".
- * @param idx index returned in this parameter if return value is "index".
- * @return -1 for "EOF", 0 for "parse error", 1 for "tag key", 2 for "index", 3 for "period"
- */
-static int readNextToken(const char *c, int& pos, DcmTagKey& key, Uint32& idx)
-{
-  OFString aString;
-  int lpos = pos;
-  int spos = 0;
-  while(isspace(OFstatic_cast(unsigned char, c[lpos]))) ++lpos; // ignore leading space
-
-  if (c[lpos]=='\0') return -1; // EOF
-  if (c[lpos]=='.')
-  {
-    ++pos;
-    return 3; // period
-  }
-  if (c[lpos]=='[')
-  {
-    spos = ++lpos;
-    while ((c[lpos] >= '0')&&(c[lpos] <= '9')) ++lpos;
-    if (c[lpos] != ']') return 0; // parse error
-    unsigned long newindex = 0;
-    if (1 != sscanf(c+spos,"%lu", &newindex)) return 0; // parse error
-    idx = OFstatic_cast(Uint32, newindex);
-    pos = ++lpos;
-    return 2; // index
-  }
-  if (c[lpos]=='(')
-  {
-    spos = ++lpos;
-    while ((c[lpos] != ')')&&(c[lpos] != '\0')) ++lpos;
-    if (c[lpos] != ')') return 0; // parse error
-    unsigned int group=0;
-    unsigned int elem=0;
-    if (2 != sscanf(c+spos,"%x,%x", &group, &elem)) return 0; // parse error
-    key = DcmTagKey(group,elem);
-    pos = ++lpos;
-    return 1; // tag key
-  }
-  spos = lpos;
-  while ( ((c[lpos] >= 'a')&&(c[lpos] <= 'z')) || ((c[lpos] >= 'A')&&(c[lpos] <= 'Z')) || ((c[lpos] >= '0')&&(c[lpos] <= '9'))) ++lpos;
-  aString.append(c + spos, (lpos-spos));
-  const DcmDataDictionary& globalDataDict = dcmDataDict.rdlock();
-  const DcmDictEntry *dicent = globalDataDict.findEntry(aString.c_str());
-  if (dicent)
-  {
-    key = dicent->getKey();
-    dcmDataDict.rdunlock();
-    pos = lpos;
-    return 1; // tag key;
-  }
-  dcmDataDict.rdunlock();
-  OFLOG_ERROR(dcmsignLogger, "attribute name '" << aString.c_str() << "' unknown.");
-  return 0; // parse error
-}
-
-/* reads a complete text file (max 64K) into a memory block
- * and returns a pointer to the memory block.
- * memory must be freed by called.
- * @param filename file to be read
- * @return pointer to memory block if successful, NULL otherwise.
- */
-static char *readTextFile(const char *filename)
-{
-  char *result = NULL;
-  FILE *file = fopen(filename, "rb");
-  if (file)
-  {
-    fseek(file, 0, SEEK_END);
-    long numBytes = ftell(file);
-    fseek(file, 0, SEEK_SET);
-    if (numBytes > 65536)
-    {
-      OFLOG_WARN(dcmsignLogger, "text file too large, ignoring everything beyond 64K.");
-      numBytes = 65536;
-    }
-    result = new char[numBytes];
-    if (result)
-    {
-      if (OFstatic_cast(size_t, numBytes) != fread(result, 1, OFstatic_cast(size_t, numBytes), file))
-      {
-        OFLOG_WARN(dcmsignLogger, "read error in file " << filename);
-        delete[] result;
-        result = NULL;
-      }
-    }
-    fclose(file);
-  } else {
-    OFLOG_ERROR(dcmsignLogger, "file not found: " << filename);
-  }
-  return result;
-}
-
-/* reads a list of attributes from a text file.
- * The attributes can be in the form (gggg,eeee) or can be dictionary names,
- * separated by arbitrary whitespace.
- * @param filename file to be read from
- * @param tagList attribute tags are added to this list
- * @return 0 if successful, a program exit code otherwise
- */
-static int parseTextFile(const char *filename, DcmAttributeTag& tagList)
-{
-  char *c=readTextFile(filename);
-  if (c==NULL) return 10; // bail out
-  int position = 0;
-  int token = 0;
-  Uint32 idx = 0;
-  DcmTagKey key;
-  int result = 0;
-  do
-  {
-    token = readNextToken(c, position, key, idx);
-    if (token == 1) // we have read a tag key
-    {
-      if (EC_Normal != tagList.putTagVal(key, tagList.getVM()))
-      {
-        result = 10;
-        token = -1;
-      }
-    }
-    else if (token >= 0)
-    {
-      OFLOG_ERROR(dcmsignLogger, "parse error in text file '" << filename << "'");
-      result = 10;
-      token = -1;
-    }
-  } while (token >= 0);
-  delete[] c;
-  return result;
-}
-
-
-/* locates a specific item within the given dataset.
- * @param dataset dataset to be searched
- * @param location location string. Format is "sequence[item]{.sequence[item]}*"
- *   Where sequence can be (gggg,eeee) or a dictionary name and items
- *   within sequences are counted from zero.
- * @return pointer to the item searched if found, NULL otherwise
- */
-static DcmItem *locateItemforSignatureCreation(DcmItem& dataset, const char *location)
-{
-  DcmTagKey key;
-  Uint32 idx;
-  int pos = 0;
-  int token = 0;
-  int expected = 1;
-  OFBool finished = OFFalse;
-  DcmItem *result = &dataset;
-  DcmSequenceOfItems *sq = NULL;
-  DcmStack stack;
-  do
-  {
-    token = readNextToken(location, pos, key, idx);
-    if ((token != expected)&&(token != -1))
-    {
-      OFLOG_ERROR(dcmsignLogger, "parse error in item location string '" << location << "'");
-      return NULL;
-    }
-    if (token == -1)
-    {
-      if (! finished)
-      {
-        OFLOG_ERROR(dcmsignLogger, "item location string '" << location << "' incomplete.");
-        return NULL;
-      }
-      return result;
-    }
-    if (token == 1)
-    {
-      // we have read a tag key
-      stack.clear();
-      if (EC_Normal != result->search(key, stack, ESM_fromHere, OFFalse))
-      {
-        OFLOG_ERROR(dcmsignLogger, "attribute " << key << " not found in dataset (item location string is '" << location << "')");
-        return NULL;
-      }
-      if (stack.top()->ident() == EVR_SQ)
-      {
-        sq = OFstatic_cast(DcmSequenceOfItems *, (stack.top()));
-      } else {
-        OFLOG_ERROR(dcmsignLogger, "attribute " << key << " is not a sequence (item location string is '" << location << "')");
-        return NULL;
-      }
-      expected = 2;
-      finished = OFFalse;
-    }
-    else if (token == 2)
-    {
-      // we have read an index
-      if (sq == NULL)
-      {
-        OFLOG_ERROR(dcmsignLogger, "sequence not found in item location string '" << location << "'");
-        return NULL;
-      }
-      if (idx >= sq->card())
-      {
-        OFLOG_ERROR(dcmsignLogger, "sequence " << sq->getTag() << " only has " << sq->card()
-          << " items, cannot locate item " << idx << " (item location string is '" << location << "')");
-        return NULL;
-      }
-      result = sq->getItem(idx);
-      if (result == NULL)
-      {
-        OFLOG_ERROR(dcmsignLogger, "item not found in item location string '" << location << "'");
-        return NULL;
-      }
-      expected = 3;
-      finished = OFTrue;
-    }
-    else if (token == 3)
-    {
-      // we have read a period
-      expected = 1;
-      finished = OFFalse;
-    }
-  } while (token > 0);
-  return NULL;
-}
-
-/* performs a signature operation on a given dataset
- * @param dataset to sign
- * @param key private key for signature
- * @param cert certificate for signature
- * @param opt_mac MAC for signature
- * @param opt_profile security profile for signature
- * @param opt_tagList list of attribute tags, may be NULL
- * @return 0 if successful, a program exit code otherwise
- */
-static int do_sign(
-  DcmItem *dataset,
-  SiPrivateKey& key,
-  SiCertificate& cert,
-  SiMAC *opt_mac,
-  SiSecurityProfile *opt_profile,
-  DcmAttributeTag *opt_tagList,
-  E_TransferSyntax opt_signatureXfer,
-  FILE *dumpFile)
-{
-  OFCondition sicond = EC_Normal;
-  DcmSignature signer;
-  signer.attach(dataset);
-  signer.setDumpFile(dumpFile);
-  sicond = signer.createSignature(key, cert, *opt_mac, *opt_profile, opt_signatureXfer, opt_tagList);
-  if (sicond != EC_Normal)
-  {
-    OFLOG_ERROR(dcmsignLogger, sicond.text() << ": while creating signature in main dataset");
-    return 1;
-  }
-  return 0;
-}
-
-/* print the location stack into the given stack.
- * It is assumed that the stack top is a DigitalSignatureSequence which is not printed
- * and that the stack bottom is the main dataset, which is also not printed.
- * @param stack search stack, as returned by DcmSignature::findFirstSignatureItem() etc.
- * @param str printable text returned in this string.
- */
-static void printSignatureItemPosition(DcmStack& stack, OFString& str)
-{
-  str.clear();
-  DcmObject *elem = NULL;
-  DcmSequenceOfItems *sq = NULL;
-  unsigned long sqCard=0;
-  const char *tagname = NULL;
-  unsigned long m=0;
-  char buf[20];
-
-  if (stack.card() > 2)
-  {
-    // signature is located within a sequence
-    for (unsigned long l=stack.card()-2; l>0; --l) // loop over all elements except the stack top and bottom
-    {
-      elem = stack.elem(l);
-      if (elem)
-      {
-        if ((elem->ident() == EVR_item) && sq)
-        {
-          sqCard = sq->card();
-          for (m=0; m<sqCard; m++)
-          {
-            if (sq->getItem(m) == elem)
-            {
-              sprintf(buf, "[%lu]", m);
-              str.append(buf);
-            }
-          }
-        }
-        else
-        {
-          if (str.size() > 0) str.append(".");
-          sq = OFstatic_cast(DcmSequenceOfItems *, elem);
-          DcmTag currentTag(elem->getTag());
-          tagname = currentTag.getTagName();
-          if (tagname) str.append(tagname); else
-          {
-            sprintf(buf, "(%04x,%04x)", elem->getTag().getGroup(), elem->getTag().getElement());
-            str.append(buf);
-          }
-          if (elem->ident() == EVR_SQ) sq = OFstatic_cast(DcmSequenceOfItems *, elem); else sq = NULL;
-        }
-      }
-    }
-  } else {
-    // signature is located in the main dataset
-    str = "Main Dataset";
-  }
-}
-
-/* performs a signature operation on a sub-item within a dataset
- * @param dataset in which to sign
- * @param key private key for signature
- * @param cert certificate for signature
- * @param opt_mac MAC for signature
- * @param opt_profile security profile for signature
- * @param opt_tagList list of attribute tags, may be NULL
- * @param location location string. Format is "sequence[item]{.sequence[item]}*"
- *   Where sequence can be (gggg,eeee) or a dictionary name and items
- *   within sequences are counted from zero.
- * @return 0 if successful, a program exit code otherwise
- */
-static int do_sign_item(
-  DcmItem *dataset,
-  SiPrivateKey& key,
-  SiCertificate& cert,
-  SiMAC *opt_mac,
-  SiSecurityProfile *opt_profile,
-  DcmAttributeTag *opt_tagList,
-  const char *opt_location,
-  E_TransferSyntax opt_signatureXfer,
-  FILE *dumpFile)
-{
-  OFCondition sicond = EC_Normal;
-  DcmSignature signer;
-  DcmItem *sigItem = locateItemforSignatureCreation(*dataset, opt_location);
-  if (sigItem == NULL) return 1;
-
-  signer.detach();
-  signer.attach(sigItem);
-  signer.setDumpFile(dumpFile);
-  sicond = signer.createSignature(key, cert, *opt_mac, *opt_profile, opt_signatureXfer, opt_tagList);
-  if (sicond != EC_Normal)
-  {
-    OFLOG_ERROR(dcmsignLogger, sicond.text() << ": while creating signature in item '" << opt_location << "'");
-    return 1;
-  }
-  signer.detach();
-  return 0;
-}
-
-/* verify all signatures in the given dataset and print results to COUT.
- * @param dataset dataset to verify
- * @return 0 if successful, a program exit code otherwise
- */
-static int do_verify(
-  DcmItem *dataset)
-{
-  OFCondition sicond = EC_Normal;
-  DcmStack stack;
-  DcmSignature signer;
-  OFString aString;
-  int counter = 0;
-  int corrupt_counter = 0;
-  unsigned long numSignatures = 0;
-  unsigned long l=0;
-  Uint16 macID = 0;
-  DcmAttributeTag at(DCM_DataElementsSigned);
-  DcmItem *sigItem = DcmSignature::findFirstSignatureItem(*dataset, stack);
-  DcmTagKey tagkey;
-  DcmTag tag;
-  const char *tagName = NULL;
-
-  while (sigItem)
-  {
-    signer.attach(sigItem);
-    numSignatures = signer.numberOfSignatures();
-    for (l=0; l<numSignatures; l++)
-    {
-      if (EC_Normal == signer.selectSignature(l))
-      {
-        ++counter;
-        if (EC_Normal == signer.getCurrentSignatureUID(aString))
-          OFLOG_WARN(dcmsignLogger, "Signature #" << counter << " UID=" << aString);
-        else
-          OFLOG_WARN(dcmsignLogger, "Signature #" << counter << " UID=" << "(unknown)");
-        printSignatureItemPosition(stack, aString);
-        if (dcmsignLogger.isEnabledFor(OFLogger::INFO_LOG_LEVEL))
-        {
-          OFLOG_INFO(dcmsignLogger, "  Location                    : " << aString);
-          if (EC_Normal == signer.getCurrentMacID(macID))
-            OFLOG_INFO(dcmsignLogger, "  MAC ID                      : " << macID);
-          else
-            OFLOG_INFO(dcmsignLogger, "  MAC ID                      : (unknown)");
-          if (EC_Normal == signer.getCurrentMacName(aString))
-            OFLOG_INFO(dcmsignLogger, "  MAC algorithm               : " << aString);
-          else
-            OFLOG_INFO(dcmsignLogger, "  MAC algorithm               : (unknown)");
-          if (EC_Normal == signer.getCurrentMacXferSyntaxName(aString))
-            OFLOG_INFO(dcmsignLogger, "  MAC calculation xfer syntax : " << aString);
-          else
-            OFLOG_INFO(dcmsignLogger, "  MAC calculation xfer syntax : (unknown)");
-          // data elements signed
-          if (EC_Normal != signer.getCurrentDataElementsSigned(at))
-            OFLOG_INFO(dcmsignLogger, "  Data elements signed        : all elements");
-          else
-          {
-            OFLOG_INFO(dcmsignLogger, "  Data elements signed        :");
-            unsigned long atVM = at.getVM();
-            for (unsigned long n=0; n<atVM; n++)
-            {
-              if (EC_Normal == at.getTagVal(tagkey, n))
-              {
-                tag = tagkey;
-                tagName = tag.getTagName();
-                OFLOG_INFO(dcmsignLogger, "      " << tagkey << " " << (tagName != NULL ? tagName : ""));
-              }
-            }
-          }
-
-          if (EC_Normal == signer.getCurrentSignatureDateTime(aString))
-            OFLOG_INFO(dcmsignLogger, "  Signature date/time         : " << aString);
-          else
-            OFLOG_INFO(dcmsignLogger, "  Signature date/time         : (unknown)");
-          OFLOG_INFO(dcmsignLogger, "  Certificate of signer       : ");
-          SiCertificate *cert = signer.getCurrentCertificate();
-          if ((cert == NULL)||(cert->getKeyType()==EKT_none))
-            OFLOG_INFO(dcmsignLogger, "      none");
-          else
-          {
-            OFLOG_INFO(dcmsignLogger, "      X.509v" << cert->getX509Version());
-            cert->getCertSubjectName(aString);
-            OFLOG_INFO(dcmsignLogger, "      Subject                 : " << aString);
-
-            cert->getCertIssuerName(aString);
-            OFLOG_INFO(dcmsignLogger, "      Issued by               : " << aString);
-            OFLOG_INFO(dcmsignLogger, "      Serial no.              : " << cert->getCertSerialNo());
-            cert->getCertValidityNotBefore(aString);
-            OFLOG_INFO(dcmsignLogger, "      Validity                : not before " << aString);
-            cert->getCertValidityNotAfter(aString);
-            OFLOG_INFO(dcmsignLogger, "      Validity                : not after " << aString);
-            switch (cert->getKeyType())
-            {
-              case EKT_RSA:
-                OFLOG_INFO(dcmsignLogger, "      Public key              : RSA, " << cert->getCertKeyBits() << " bits");
-                break;
-              case EKT_DSA:
-                OFLOG_INFO(dcmsignLogger, "      Public key              : DSA, " << cert->getCertKeyBits() << " bits");
-                break;
-              case EKT_DH:
-                OFLOG_INFO(dcmsignLogger, "      Public key              : DH, " << cert->getCertKeyBits() << " bits");
-                break;
-              case EKT_none: // should never happen
-                OFLOG_INFO(dcmsignLogger, "      Public key              : none");
-                break;
-            }
-          }
-          aString = "  Verification                : ";
-        } else {
-          OFLOG_INFO(dcmsignLogger, "  Location     : " << aString);
-          aString = "  Verification : ";
-        }
-        sicond = signer.verifyCurrent();
-        if (sicond.good())
-        {
-          OFLOG_WARN(dcmsignLogger, aString << "OK\n");
-        } else {
-          corrupt_counter++;
-          OFLOG_WARN(dcmsignLogger, aString << sicond.text() << "\n");
-        }
-      }
-    }
-    signer.detach();
-    sigItem = DcmSignature::findNextSignatureItem(*dataset, stack);
-  }
-  if (counter == 0)
-    OFLOG_WARN(dcmsignLogger, "no signatures found in dataset.");
-  else
-    OFLOG_INFO(dcmsignLogger, counter << " signatures verified in dataset, " << corrupt_counter << " corrupted.");
-  return 0;
-}
-
-/* remove all signatures from the given dataset, print action details.
- * @param dataset dataset to modify
- * @return 0 if successful, a program exit code otherwise
- */
-static int do_remove_all(
-  DcmItem *dataset)
-{
-  OFCondition sicond = EC_Normal;
-  DcmSignature signer;
-  int counter = 0;
-  OFString aString;
-  DcmStack stack;
-  DcmItem *sigItem = DcmSignature::findFirstSignatureItem(*dataset, stack);
-  while (sigItem)
-  {
-    signer.attach(sigItem);
-    while (signer.numberOfSignatures() > 0)
-    {
-      ++counter;
-      if (EC_Normal == signer.selectSignature(0))
-      {
-        if (EC_Normal == signer.getCurrentSignatureUID(aString))
-          OFLOG_WARN(dcmsignLogger, "Signature #" << counter << " UID=" << aString);
-        else
-          OFLOG_WARN(dcmsignLogger, "Signature #" << counter << " UID=(unknown)");
-        printSignatureItemPosition(stack, aString);
-        OFLOG_WARN(dcmsignLogger, "  Location                    : " << aString);
-      }
-      sicond = signer.removeSignature(0);
-      if (sicond != EC_Normal)
-      {
-        OFLOG_ERROR(dcmsignLogger, sicond.text() << ": while removing signature");
-        return 1;
-      }
-    }
-    signer.detach();
-    stack.pop(); // remove pointer to the Digital Signatures Sequence that we've just deleted.
-    sigItem = DcmSignature::findNextSignatureItem(*dataset, stack);
-  }
-
-  OFLOG_INFO(dcmsignLogger, counter << " signatures found and removed from dataset.");
-  return 0;
-}
-
-/* remove the signature with the given UID from the dataset, print action details.
- * @param dataset dataset to modify
- * @param opt_location Digital Signature UID of the signature to remove
- * @return 0 if successful, a program exit code otherwise
- */
-static int do_remove(
-  DcmItem *dataset,
-  const char *opt_location)
-{
-  OFCondition sicond = EC_Normal;
-  DcmSignature signer;
-  OFString aString;
-  DcmStack stack;
-  unsigned long cardSQ;
-  unsigned long i;
-  DcmItem *sigItem = DcmSignature::findFirstSignatureItem(*dataset, stack);
-  while (sigItem)
-  {
-    signer.attach(sigItem);
-    cardSQ = signer.numberOfSignatures();
-    for (i=0; i<cardSQ; i++)
-    {
-      if (EC_Normal == signer.selectSignature(i))
-      {
-        if (EC_Normal == signer.getCurrentSignatureUID(aString))
-        {
-          if (aString == opt_location)
-          {
-            OFLOG_WARN(dcmsignLogger, "Signature UID=" << aString);
-            printSignatureItemPosition(stack, aString);
-            OFLOG_WARN(dcmsignLogger, "  Location                    : " << aString);
-
-            sicond = signer.removeSignature(i);
-            if (sicond != EC_Normal)
-            {
-              OFLOG_ERROR(dcmsignLogger, sicond.text() << ": while removing signature");
-              return 1;
-            } else {
-              return 0;
-            }
-          }
-        }
-      }
-    }
-    signer.detach();
-    sigItem = DcmSignature::findNextSignatureItem(*dataset, stack);
-  }
-  OFLOG_ERROR(dcmsignLogger, "signature with UID '" << opt_location << "' not found.");
-  return 1;
-}
-
 
 #define SHORTCOL 4
 #define LONGCOL 21
@@ -693,13 +92,12 @@ static int do_remove(
 int main(int argc, char *argv[])
 {
   DcmSignature::initializeLibrary(); // initialize dcmsign
-
   const char *                  opt_certfile = NULL;
   OFCmdUnsignedInt              opt_filepad = 0;
   E_FileReadMode                opt_readMode = ERM_autoDetect;
   const char *                  opt_ifname = NULL;
-  OFCmdUnsignedInt              opt_itempad = 0;
   E_TransferSyntax              opt_ixfer = EXS_Unknown;
+  OFCmdUnsignedInt              opt_itempad = 0;
   const char *                  opt_keyfile = NULL;  // private key file
   int                           opt_keyFileFormat = X509_FILETYPE_PEM; // file format for certificates and private keys
   const char *                  opt_location = NULL; // location (path) within dataset
@@ -716,13 +114,26 @@ int main(int argc, char *argv[])
   DcmAttributeTag *             opt_tagList = NULL; // list of attribute tags
   E_TransferSyntax              opt_signatureXfer = EXS_Unknown;
   FILE *                        opt_dumpFile = NULL;
-  int result = 0;
+  SiTimeStampFS *               opt_timeStamp = NULL;
+  const char *                  opt_ts_queryfile = NULL;
+  const char *                  opt_ts_responsefile = NULL;
+  const char *                  opt_ts_uidfile = NULL;
+  const char *                  opt_ts_policyoid = NULL;
+  E_SignatureVerificationPolicy opt_verificationPolicy = ESVP_verifyIfPresent;
+  E_TimestampVerificationPolicy opt_timestampPolicy = ETVP_verifyTSIfPresent;
+  SiCertificateVerifier         certVerifier;
+  DcmDataset *dataset = NULL;
+  SiCertificate cert;
+  SiPrivateKey key;
+  OFCondition sicond;
+  DcmFileFormat fileformat;
 
+  SiSignaturePurpose::E_SignaturePurposeType opt_sigPurpose = SiSignaturePurpose::ESP_none;
+  int result = EXITCODE_NO_ERROR;
   OFConsoleApplication app(OFFIS_CONSOLE_APPLICATION , APPLICATION_ABSTRACT, rcsid);
   OFCommandLine cmd;
   cmd.setOptionColumns(LONGCOL, SHORTCOL);
   cmd.setParamColumn(LONGCOL + SHORTCOL + 4);
-
   cmd.addParam("dcmfile-in",  "DICOM input filename to be processed");
   cmd.addParam("dcmfile-out", "DICOM output filename", OFCmdParam::PM_Optional);
 
@@ -742,6 +153,9 @@ int main(int argc, char *argv[])
       cmd.addOption("--read-xfer-little",          "-te",       "read with explicit VR little endian TS");
       cmd.addOption("--read-xfer-big",             "-tb",       "read with explicit VR big endian TS");
       cmd.addOption("--read-xfer-implicit",        "-ti",       "read with implicit VR little endian TS");
+    cmd.addSubGroup("handling of defined length UN elements:");
+      cmd.addOption("--retain-un",                 "-uc",       "retain elements as UN (default)");
+      cmd.addOption("--convert-un",                "+uc",       "convert to real VR if known");
 
   cmd.addGroup("signature commands:", LONGCOL, SHORTCOL + 2);
       cmd.addOption("--verify",                                 "verify all signatures (default)");
@@ -749,38 +163,95 @@ int main(int argc, char *argv[])
                                                                 "create signature in main object");
       cmd.addOption("--sign-item",                 "+si",    3, "[k]eyfile, [c]ertfile, [i]tem location: string",
                                                                 "create signature in sequence item");
+      cmd.addOption("--insert-timestamp",          "+t",     3, "ts[q]file, ts[r]file [u]idfile: string",
+                                                                "insert certified timestamp from ts response r\n"
+                                                                "from timestamp query q at signature UID u");
       cmd.addOption("--remove",                    "+r",     1, "[s]ignature UID: string", "remove signature");
       cmd.addOption("--remove-all",                "+ra",       "remove all signatures from data set");
 
+  cmd.addGroup("general signature options:");
+    cmd.addSubGroup("key and certificate file format:");
+      cmd.addOption("--pem-keys",                 "-pem",       "read keys/certificates as PEM file (default)");
+      cmd.addOption("--der-keys",                 "-der",       "read keys/certificates as DER file");
+    cmd.addSubGroup("signature format:");
+      cmd.addOption("--format-new",               "-fn",        "use correct DICOM signature format (default)");
+      cmd.addOption("--format-old",               "-fo",        "use old (pre-3.5.4) DCMTK signature format");
+
+  cmd.addGroup("signature verification options (only with --verify):");
+    cmd.addSubGroup("signature verification:");
+      cmd.addOption("--verify-if-present",         "+rv",       "verify signatures if present, pass otherwise\n(default)");
+      cmd.addOption("--require-sig",               "+rg",       "fail if no signature at all is present");
+      cmd.addOption("--require-creator",           "+rc",       "fail if no creator RSA signature is present");
+      cmd.addOption("--require-auth",              "+ru",       "fail if no auth RSA signature is present");
+      cmd.addOption("--require-sr",                "+rs",       "fail if no SR RSA signature is present");
+    cmd.addSubGroup("timestamp verification:");
+      cmd.addOption("--verify-ts",                 "+tv",       "verify certified timestamp if present (default)");
+      cmd.addOption("--ignore-ts",                 "-tv",       "ignore certified timestamps");
+      cmd.addOption("--require-ts",                "+tr",       "fail if no certified timestamp is present");
+    cmd.addSubGroup("certification authority:");
+      cmd.addOption("--add-cert-file",             "+cf",    1, "[f]ilename: string",
+                                                                "add trusted certificate file to cert store");
+      cmd.addOption("--add-ucert-file",            "+uf",    1, "[f]ilename: string",
+                                                                "add untrusted intermediate certificate file");
+      cmd.addOption("--add-cert-dir",              "+cd",    1, "[d]irectory: string",
+                                                                "add certificates in d to cert store");
+      cmd.addOption("--add-crl-file",              "+cr",    1, "[f]ilename: string",
+                                                                "add certificate revocation list file\n(implies --enable-crl-vfy)");
+      cmd.addOption("--enable-crl-vfy",            "+cl",       "enable CRL verification");
+
   cmd.addGroup("signature creation options (only with --sign or --sign-item):");
     cmd.addSubGroup("private key password:");
       cmd.addOption("--std-passwd",               "+ps",        "prompt user to type password on stdin (default)");
       cmd.addOption("--use-passwd",               "+pw",    1,  "[p]assword: string ",
                                                                 "use specified password");
       cmd.addOption("--null-passwd",              "-pw",        "use empty string as password");
-    cmd.addSubGroup("key and certificate file format:");
-      cmd.addOption("--pem-keys",                 "-pem",       "read keys/certificates as PEM file (default)");
-      cmd.addOption("--der-keys",                 "-der",       "read keys/certificates as DER file");
     cmd.addSubGroup("digital signature profile:");
       cmd.addOption("--profile-none",             "-pf",        "don't enforce any signature profile (default)");
       cmd.addOption("--profile-base",             "+pb",        "enforce base RSA signature profile");
       cmd.addOption("--profile-creator",          "+pc",        "enforce creator RSA signature profile");
       cmd.addOption("--profile-auth",             "+pa",        "enforce authorization signature profile");
+      cmd.addOption("--profile-sr",               "+pr",        "enforce SR RSA signature profile");
+      cmd.addOption("--profile-srv" ,             "+pv",        "enforce SR RSA signature profile (verification)");
     cmd.addSubGroup("MAC algorithm:");
       cmd.addOption("--mac-ripemd160",            "+mr",        "use RIPEMD 160 (default)");
-      cmd.addOption("--mac-sha1",                 "+ms",        "use SHA-1");
-      cmd.addOption("--mac-md5",                  "+mm",        "use MD 5");
+      cmd.addOption("--mac-sha1",                 "+ms",        "use SHA-1 (not recommended)");
+      cmd.addOption("--mac-md5",                  "+mm",        "use MD5 (not recommended)");
       cmd.addOption("--mac-sha256",               "+m2",        "use SHA-256");
       cmd.addOption("--mac-sha384",               "+m3",        "use SHA-384");
       cmd.addOption("--mac-sha512",               "+m5",        "use SHA-512");
-
+    cmd.addSubGroup("signature purpose:");
+      cmd.addOption("--list-purposes",            "+lp",        "show list of signature purpose codes and exit", OFCommandLine::AF_Exclusive);
+      cmd.addOption("--no-sig-purpose",           "-sp",        "do not add signature purpose (default)");
+      cmd.addOption("--sig-purpose",              "+sp",     1, "[p]urpose code: integer (1..18)",
+                                                                "add digital signature purpose code p");
     cmd.addSubGroup("tag selection:");
-      cmd.addOption("--tag",                      "-t",      1, "[t]ag: \"gggg,eeee\" or dictionary name", "sign only specified tag\n(this option can be specified multiple times)");
-      cmd.addOption("--tag-file",                 "-tf",     1, "[f]ilename: string", "read list of tags from text file");
-    cmd.addSubGroup("signature format:");
-      cmd.addOption("--format-new",               "-fn",        "use correct DICOM signature format (default)");
-      cmd.addOption("--format-old",               "-fo",        "use old (pre-3.5.4) DCMTK signature format,\n"
-                                                                "non-conformant if signature includes\ncompressed pixel data");
+      cmd.addOption("--tag",                      "-t",      1, "[t]ag: \"gggg,eeee\" or dictionary name",
+                                                                "sign only specified tag\n(this option can be specified multiple times)");
+      cmd.addOption("--tag-file",                 "-tf",     1, "[f]ilename: string",
+                                                                "read list of tags from text file");
+
+  cmd.addGroup("timestamp creation options (only with --sign or --sign-item):");
+    cmd.addSubGroup("timestamp creation:");
+      cmd.addOption("--timestamp-off",            "-ts",        "do not create timestamp (default)");
+      cmd.addOption("--timestamp-file",           "+ts",     2, "[t]sq-filename, [u]id-filename: string",
+                                                                "create timestamp query file t and uid file u");
+    cmd.addSubGroup("timestamp MAC algorithm (only with --timestamp-file):");
+      cmd.addOption("--ts-mac-sha256",            "+tm2",       "use SHA-256 (default)");
+      cmd.addOption("--ts-mac-sha384",            "+tm3",       "use SHA-384");
+      cmd.addOption("--ts-mac-sha512",            "+tm5",       "use SHA-512");
+      cmd.addOption("--ts-mac-ripemd160",         "+tmr",       "use RIPEMD 160");
+      cmd.addOption("--ts-mac-sha1",              "+tms",       "use SHA-1 (not recommended)");
+      cmd.addOption("--ts-mac-md5",               "+tmm",       "use MD5 (not recommended)");
+    cmd.addSubGroup("timestamp query nonce options (only with --timestamp-file):");
+      cmd.addOption("--ts-use-nonce",             "+tn",        "include random nonce (default)");
+      cmd.addOption("--ts-no-nonce",              "-tn",        "do not include nonce");
+    cmd.addSubGroup("timestamp certificate inclusion options (only with --timestamp-file):");
+      cmd.addOption("--ts-request-cert",          "+tc",        "request TSA certificate in timestamp (default)");
+      cmd.addOption("--ts-no-cert",               "-tc",        "do not request TSA certificate in timestamp");
+    cmd.addSubGroup("timestamp policy options (only with --timestamp-file):");
+      cmd.addOption("--ts-no-policy",             "-tp",        "do not specify ts policy (default)");
+      cmd.addOption("--ts-policy",                "+tp",     1, "[p]olicy-OID: string",
+                                                                "request timestamp policy p");
   cmd.addGroup("output options:");
     cmd.addSubGroup("output transfer syntax:");
       cmd.addOption("--write-xfer-same",          "+t=",        "write with same TS as input (default)");
@@ -793,7 +264,6 @@ int main(int argc, char *argv[])
     cmd.addSubGroup("other output options:");
       cmd.addOption("--dump",                      "+d",     1, "[f]ilename: string",
                                                                 "dump byte stream fed into the MAC codec to file\n(only with --sign or --sign-item)");
-
   /* evaluate command line */
   prepareCmdLineArgs(argc, argv, OFFIS_CONSOLE_APPLICATION);
   if (app.parseCommandLine(cmd, argc, argv))
@@ -801,30 +271,37 @@ int main(int argc, char *argv[])
     /* check exclusive options first */
     if (cmd.hasExclusiveOption())
     {
-        if (cmd.findOption("--version"))
-        {
-            app.printHeader(OFTrue /*print host identifier*/);
-            COUT << OFendl << "External libraries used:";
+      if (cmd.findOption("--version"))
+      {
+        app.printHeader(OFTrue /*print host identifier*/);
+        COUT << OFendl << "External libraries used:";
 #if !defined(WITH_ZLIB) && !defined(WITH_OPENSSL)
-            COUT << " none" << OFendl;
+        COUT << " none" << OFendl;
 #else
-            COUT << OFendl;
+        COUT << OFendl;
 #endif
 #ifdef WITH_ZLIB
-            COUT << "- ZLIB, Version " << zlibVersion() << OFendl;
+        COUT << "- ZLIB, Version " << zlibVersion() << OFendl;
 #endif
 #ifdef WITH_OPENSSL
-            COUT << "- " << OPENSSL_VERSION_TEXT << OFendl;
+#ifdef OPENSSL_NO_EC
+        COUT << "- " << OPENSSL_VERSION_TEXT << ", without ECDSA support" << OFendl;
+#else
+        COUT << "- " << OPENSSL_VERSION_TEXT << ", with ECDSA support" << OFendl;
 #endif
-            return 0;
-        }
+#endif
+        return EXITCODE_NO_ERROR;
+      }
+      if (cmd.findOption("--list-purposes"))
+      {
+        app.printHeader(OFTrue /*print host identifier*/);
+        SiSignaturePurpose::printSignatureCodes(COUT);
+        return EXITCODE_NO_ERROR;
+      }
     }
-
     /* command line parameters */
-
     cmd.getParam(1, opt_ifname);
     if (cmd.getParamCount() > 1) cmd.getParam(2, opt_ofname);
-
     OFLog::configureFromCommandLine(cmd, app);
 
     cmd.beginOptionBlock();
@@ -832,29 +309,31 @@ int main(int argc, char *argv[])
     if (cmd.findOption("--read-file-only")) opt_readMode = ERM_fileOnly;
     if (cmd.findOption("--read-dataset")) opt_readMode = ERM_dataset;
     cmd.endOptionBlock();
-
     cmd.beginOptionBlock();
-    if (cmd.findOption("--read-xfer-auto"))
-        opt_ixfer = EXS_Unknown;
-    if (cmd.findOption("--read-xfer-detect"))
-        dcmAutoDetectDatasetXfer.set(OFTrue);
+    if (cmd.findOption("--read-xfer-auto")) opt_ixfer = EXS_Unknown;
+    if (cmd.findOption("--read-xfer-detect")) dcmAutoDetectDatasetXfer.set(OFTrue);
     if (cmd.findOption("--read-xfer-little"))
     {
-        app.checkDependence("--read-xfer-little", "--read-dataset", opt_readMode == ERM_dataset);
-        opt_ixfer = EXS_LittleEndianExplicit;
+      app.checkDependence("--read-xfer-little", "--read-dataset", opt_readMode == ERM_dataset);
+      opt_ixfer = EXS_LittleEndianExplicit;
     }
     if (cmd.findOption("--read-xfer-big"))
     {
-        app.checkDependence("--read-xfer-big", "--read-dataset", opt_readMode == ERM_dataset);
-        opt_ixfer = EXS_BigEndianExplicit;
+      app.checkDependence("--read-xfer-big", "--read-dataset", opt_readMode == ERM_dataset);
+      opt_ixfer = EXS_BigEndianExplicit;
     }
     if (cmd.findOption("--read-xfer-implicit"))
     {
-        app.checkDependence("--read-xfer-implicit", "--read-dataset", opt_readMode == ERM_dataset);
-        opt_ixfer = EXS_LittleEndianImplicit;
+      app.checkDependence("--read-xfer-implicit", "--read-dataset", opt_readMode == ERM_dataset);
+      opt_ixfer = EXS_LittleEndianImplicit;
     }
     cmd.endOptionBlock();
 
+    cmd.beginOptionBlock();
+    if (cmd.findOption("--retain-un")) dcmEnableUnknownVRConversion.set(OFFalse);
+    if (cmd.findOption("--convert-un")) dcmEnableUnknownVRConversion.set(OFTrue);
+    cmd.endOptionBlock();
+
     cmd.beginOptionBlock();
     if (cmd.findOption("--verify"))
     {
@@ -875,6 +354,18 @@ int main(int argc, char *argv[])
       app.checkValue(cmd.getValue(opt_certfile));
       app.checkValue(cmd.getValue(opt_location));
     }
+    if (cmd.findOption("--insert-timestamp"))
+    {
+      opt_operation = DSO_insertTimestamp;
+      if (opt_ofname == NULL) app.printError("parameter dcmfile-out required for --insert-timestamp");
+      app.checkValue(cmd.getValue(opt_ts_queryfile));
+      app.checkValue(cmd.getValue(opt_ts_responsefile));
+      app.checkValue(cmd.getValue(opt_ts_uidfile));
+      opt_timeStamp = new SiTimeStampFS();
+      opt_timeStamp->setTSQFilename(opt_ts_queryfile);
+      opt_timeStamp->setTSRFilename(opt_ts_responsefile);
+      opt_timeStamp->setUIDFilename(opt_ts_uidfile);
+    }
     if (cmd.findOption("--remove"))
     {
       opt_operation = DSO_remove;
@@ -887,9 +378,117 @@ int main(int argc, char *argv[])
       if (opt_ofname == NULL) app.printError("parameter dcmfile-out required for --remove-all");
     }
     cmd.endOptionBlock();
-
     if ((opt_operation == DSO_verify) && opt_ofname) app.printError("parameter dcmfile-out not allowed for --verify");
 
+    cmd.beginOptionBlock();
+    if (cmd.findOption("--pem-keys")) opt_keyFileFormat = X509_FILETYPE_PEM;
+    if (cmd.findOption("--der-keys")) opt_keyFileFormat = X509_FILETYPE_ASN1;
+    cmd.endOptionBlock();
+
+    cmd.beginOptionBlock();
+    if (cmd.findOption("--verify-if-present"))
+    {
+      app.checkDependence("--verify-if-present", "--verify", (opt_operation == DSO_verify));
+      opt_verificationPolicy = ESVP_verifyIfPresent;
+    }
+    if (cmd.findOption("--require-sig"))
+    {
+      app.checkDependence("--require-sig", "--verify", (opt_operation == DSO_verify));
+      opt_verificationPolicy = ESVP_requireSignature;
+    }
+    if (cmd.findOption("--require-creator"))
+    {
+      app.checkDependence("--require-creator", "--verify", (opt_operation == DSO_verify));
+      opt_verificationPolicy = ESVP_requireCreatorRSASignature;
+    }
+    if (cmd.findOption("--require-auth"))
+    {
+      app.checkDependence("--require-auth", "--verify", (opt_operation == DSO_verify));
+      opt_verificationPolicy = ESVP_requireAuthorizationRSASignature;
+    }
+    if (cmd.findOption("--require-sr"))
+    {
+      app.checkDependence("--require-sr", "--verify", (opt_operation == DSO_verify));
+      opt_verificationPolicy = ESVP_requireSRRSASignature;
+    }
+    cmd.endOptionBlock();
+
+    cmd.beginOptionBlock();
+    if (cmd.findOption("--verify-ts"))
+    {
+      app.checkDependence("--verify-ts", "--verify", (opt_operation == DSO_verify));
+      opt_timestampPolicy = ETVP_verifyTSIfPresent;
+    }
+    if (cmd.findOption("--ignore-ts"))
+    {
+      app.checkDependence("--ignore-ts", "--verify", (opt_operation == DSO_verify));
+      opt_timestampPolicy = ETVP_ignoreTS;
+    }
+    if (cmd.findOption("--require-ts"))
+    {
+      app.checkDependence("--require-ts", "--verify", (opt_operation == DSO_verify));
+      opt_timestampPolicy = ETVP_requireTS;
+    }
+    cmd.endOptionBlock();
+
+    if (cmd.findOption("--add-cert-file", 0, OFCommandLine::FOM_First))
+    {
+      app.checkDependence("--add-cert-file", "--verify", (opt_operation == DSO_verify));
+      const char *current = NULL;
+      do
+      {
+        app.checkValue(cmd.getValue(current));
+        if (certVerifier.addTrustedCertificateFile(current, opt_keyFileFormat).bad())
+        {
+          DCMSIGN_WARN("unable to load certificate file '" << current << "', ignoring");
+        }
+      } while (cmd.findOption("--add-cert-file", 0, OFCommandLine::FOM_Next));
+    }
+    if (cmd.findOption("--add-ucert-file", 0, OFCommandLine::FOM_First))
+    {
+      app.checkDependence("--add-ucert-file", "--verify", (opt_operation == DSO_verify));
+      const char *current = NULL;
+      do
+      {
+        app.checkValue(cmd.getValue(current));
+        if (certVerifier.addUntrustedCertificateFile(current, opt_keyFileFormat).bad())
+        {
+          DCMSIGN_WARN("unable to load certificate file '" << current << "', ignoring");
+        }
+      } while (cmd.findOption("--add-ucert-file", 0, OFCommandLine::FOM_Next));
+    }
+    if (cmd.findOption("--add-cert-dir", 0, OFCommandLine::FOM_First))
+    {
+      app.checkDependence("--add-cert-dir", "--verify", (opt_operation == DSO_verify));
+      const char *current = NULL;
+      do
+      {
+        app.checkValue(cmd.getValue(current));
+        if (certVerifier.addTrustedCertificateDir(current, opt_keyFileFormat).bad())
+        {
+          DCMSIGN_WARN("unable to load certificates from directory '" << current << "', ignoring");
+        }
+      } while (cmd.findOption("--add-cert-dir", 0, OFCommandLine::FOM_Next));
+    }
+    if (cmd.findOption("--add-crl-file", 0, OFCommandLine::FOM_First))
+    {
+      app.checkDependence("--add-crl-file", "--verify", (opt_operation == DSO_verify));
+      const char *current = NULL;
+      do
+      {
+        app.checkValue(cmd.getValue(current));
+        if (certVerifier.addCertificateRevocationList(current, opt_keyFileFormat).bad())
+        {
+            DCMSIGN_WARN("unable to load CRL file '" << current << "', ignoring");
+        }
+      } while (cmd.findOption("--add-crl-file", 0, OFCommandLine::FOM_Next));
+    }
+    if (cmd.findOption("--enable-crl-vfy"))
+    {
+      app.checkDependence("--enable-crl-vfy", "--verify", (opt_operation == DSO_verify));
+      certVerifier.setCRLverification(OFTrue);
+    }
+
     cmd.beginOptionBlock();
     if (cmd.findOption("--std-passwd"))
     {
@@ -907,12 +506,6 @@ int main(int argc, char *argv[])
       opt_passwd = "";
     }
     cmd.endOptionBlock();
-
-    cmd.beginOptionBlock();
-    if (cmd.findOption("--pem-keys")) opt_keyFileFormat = X509_FILETYPE_PEM;
-    if (cmd.findOption("--der-keys")) opt_keyFileFormat = X509_FILETYPE_ASN1;
-    cmd.endOptionBlock();
-
     cmd.beginOptionBlock();
     if (cmd.findOption("--profile-none"))
     {
@@ -921,22 +514,41 @@ int main(int argc, char *argv[])
     }
     if (cmd.findOption("--profile-base"))
     {
+      // the RSA base profile can be used on dataset and item level
       app.checkDependence("--profile-base", "--sign or --sign-item", (opt_operation == DSO_sign) || (opt_operation == DSO_signItem));
       opt_profile = new SiBaseRSAProfile();
     }
     if (cmd.findOption("--profile-creator"))
     {
-      app.checkDependence("--profile-creator", "--sign or --sign-item", (opt_operation == DSO_sign) || (opt_operation == DSO_signItem));
+      // the creator RSA profile only makes sense when applied on main dataset level
+      app.checkDependence("--profile-creator", "--sign", (opt_operation == DSO_sign));
       opt_profile = new SiCreatorProfile();
     }
     if (cmd.findOption("--profile-auth"))
     {
-      app.checkDependence("--profile-auth", "--sign or --sign-item", (opt_operation == DSO_sign) || (opt_operation == DSO_signItem));
+      // the authorization RSA profile only makes sense when applied on main dataset level
+      app.checkDependence("--profile-auth", "--sign", (opt_operation == DSO_sign));
       opt_profile = new SiAuthorizationProfile();
+      DCMSIGN_WARN(
+       "The Authorization RSA Digital Signature Profile requires that any\n"
+       "attributes whose values are verifiable by the technician or physician\n"
+       "(e.g., their values are displayed to the technician or physician) must\n"
+       "be included in the signature. Please assure this using --tag options." );
+    }
+    if (cmd.findOption("--profile-sr"))
+    {
+      // the SR RSA profile only makes sense when applied on main dataset level
+      app.checkDependence("--profile-sr", "--sign", (opt_operation == DSO_sign));
+      opt_profile = new SiStructuredReportingProfile();
+    }
+    if (cmd.findOption("--profile-srv"))
+    {
+      // the SR RSA profile only makes sense when applied on main dataset level
+      app.checkDependence("--profile-srv", "--sign", (opt_operation == DSO_sign));
+      opt_profile = new SiStructuredReportingVerificationProfile();
     }
     cmd.endOptionBlock();
     if (opt_profile == NULL) opt_profile = new SiNullProfile();
-
     cmd.beginOptionBlock();
     if (cmd.findOption("--mac-ripemd160"))
     {
@@ -968,22 +580,40 @@ int main(int argc, char *argv[])
       app.checkDependence("--mac-sha512", "--sign or --sign-item", (opt_operation == DSO_sign) || (opt_operation == DSO_signItem));
       opt_mac = new SiSHA512();
     }
-
     cmd.endOptionBlock();
     if (opt_mac == NULL) opt_mac = new SiRIPEMD160();
 
+    cmd.beginOptionBlock();
+    if (cmd.findOption("--no-sig-purpose"))
+    {
+      app.checkDependence("--no-sig-purpose", "--sign or --sign-item", (opt_operation == DSO_sign) || (opt_operation == DSO_signItem));
+      opt_sigPurpose = SiSignaturePurpose::ESP_none;
+    }
+    if (cmd.findOption("--sig-purpose"))
+    {
+      app.checkDependence("--sig-purpose", "--sign or --sign-item", (opt_operation == DSO_sign) || (opt_operation == DSO_signItem));
+      OFCmdUnsignedInt val = 0;
+      app.checkValue(cmd.getValueAndCheckMinMax(val, 1, 18));
+      opt_sigPurpose = SiSignaturePurpose::lookup(OFstatic_cast(size_t, val));
+      if (opt_sigPurpose == SiSignaturePurpose::ESP_none)
+      {
+          // should never happen
+          DCMSIGN_WARN("unknown digital signature purpose code, ignoring.");
+      }
+    }
+    cmd.endOptionBlock();
+
     if (cmd.findOption("--tag-file"))
     {
       app.checkValue(cmd.getValue(opt_tagFile));
       opt_tagList = new DcmAttributeTag(DCM_DataElementsSigned);
-      result = parseTextFile(opt_tagFile, *opt_tagList);
+      result = DcmSignatureHelper::parseTextFile(opt_tagFile, *opt_tagList);
       if (result > 0)
       {
-        OFLOG_FATAL(dcmsignLogger, "Error while reading tag file '" << opt_tagFile << "', giving up.");
-        return result;
+        DCMSIGN_FATAL("Error while reading tag file '" << opt_tagFile << "', giving up.");
+        goto cleanup;
       }
     }
-
     if (cmd.findOption("--tag", 0, OFCommandLine::FOM_First))
     {
       const char *current=NULL;
@@ -991,31 +621,121 @@ int main(int argc, char *argv[])
       do
       {
         app.checkValue(cmd.getValue(current));
-        if (! addTag(current, *opt_tagList))
+        if (! DcmSignatureHelper::addTag(current, *opt_tagList))
         {
-          OFLOG_FATAL(dcmsignLogger, "unknown attribute tag '" << current << "'");
-          return 10;
+          DCMSIGN_FATAL("unknown attribute tag '" << current << "'");
+          result = EXITCODE_COMMANDLINE_SYNTAX_ERROR;
+          goto cleanup;
         }
       } while (cmd.findOption("--tag", 0, OFCommandLine::FOM_Next));
     }
-
     cmd.beginOptionBlock();
     if (cmd.findOption("--format-new")) dcmEnableOldSignatureFormat.set(OFFalse);
     if (cmd.findOption("--format-old")) dcmEnableOldSignatureFormat.set(OFTrue);
     cmd.endOptionBlock();
 
+    // timestamp command line options
+    cmd.beginOptionBlock();
+    if (cmd.findOption("--timestamp-off"))
+    {
+      app.checkDependence("--timestamp-off", "--sign or --sign-item", (opt_operation == DSO_sign) || (opt_operation == DSO_signItem));
+      opt_timeStamp = NULL;
+    }
+    if (cmd.findOption("--timestamp-file"))
+    {
+      app.checkDependence("--timestamp-file", "--sign or --sign-item", (opt_operation == DSO_sign) || (opt_operation == DSO_signItem));
+      app.checkValue(cmd.getValue(opt_ts_queryfile));
+      app.checkValue(cmd.getValue(opt_ts_uidfile));
+      opt_timeStamp = new SiTimeStampFS();
+      opt_timeStamp->setTSQFilename(opt_ts_queryfile);
+      opt_timeStamp->setUIDFilename(opt_ts_uidfile);
+    }
+    cmd.endOptionBlock();
+
+    cmd.beginOptionBlock();
+    if (cmd.findOption("--ts-mac-sha256"))
+    {
+      app.checkDependence("--ts-mac-sha256", "--timestamp-file", (opt_timeStamp != NULL));
+      opt_timeStamp->setMAC(EMT_SHA256);
+    }
+    if (cmd.findOption("--ts-mac-sha384"))
+    {
+      app.checkDependence("--ts-mac-sha384", "--timestamp-file", (opt_timeStamp != NULL));
+      opt_timeStamp->setMAC(EMT_SHA384);
+    }
+    if (cmd.findOption("--ts-mac-sha512"))
+    {
+      app.checkDependence("--ts-mac-sha512", "--timestamp-file", (opt_timeStamp != NULL));
+      opt_timeStamp->setMAC(EMT_SHA512);
+    }
+    if (cmd.findOption("--ts-mac-ripemd160"))
+    {
+      app.checkDependence("--ts-mac-ripemd160", "--timestamp-file", (opt_timeStamp != NULL));
+      opt_timeStamp->setMAC(EMT_RIPEMD160);
+    }
+    if (cmd.findOption("--ts-mac-sha1"))
+    {
+      app.checkDependence("--ts-mac-sha1", "--timestamp-file", (opt_timeStamp != NULL));
+      opt_timeStamp->setMAC(EMT_SHA1);
+    }
+    if (cmd.findOption("--ts-mac-md5"))
+    {
+      app.checkDependence("--ts-mac-md5", "--timestamp-file", (opt_timeStamp != NULL));
+      opt_timeStamp->setMAC(EMT_MD5);
+    }
+    cmd.endOptionBlock();
+
+    cmd.beginOptionBlock();
+    if (cmd.findOption("--ts-use-nonce"))
+    {
+      app.checkDependence("--ts-use-nonce", "--timestamp-file", (opt_timeStamp != NULL));
+      opt_timeStamp->setNonce(OFTrue);
+    }
+    if (cmd.findOption("--ts-no-nonce"))
+    {
+      app.checkDependence("--ts-no-nonce", "--timestamp-file", (opt_timeStamp != NULL));
+      opt_timeStamp->setNonce(OFFalse);
+    }
+    cmd.endOptionBlock();
+
+    cmd.beginOptionBlock();
+    if (cmd.findOption("--ts-request-cert"))
+    {
+      app.checkDependence("--ts-request-cert", "--timestamp-file", (opt_timeStamp != NULL));
+      opt_timeStamp->setCertificateRequested(OFTrue);
+    }
+    if (cmd.findOption("--ts-no-cert"))
+    {
+      app.checkDependence("--ts-no-cert", "--timestamp-file", (opt_timeStamp != NULL));
+      opt_timeStamp->setCertificateRequested(OFFalse);
+    }
+    cmd.endOptionBlock();
+
+    cmd.beginOptionBlock();
+    if (cmd.findOption("--ts-no-policy"))
+    {
+      app.checkDependence("--ts-no-policy", "--timestamp-file", (opt_timeStamp != NULL));
+      opt_timeStamp->setPolicyOID(NULL);
+    }
+    if (cmd.findOption("--ts-policy"))
+    {
+      app.checkDependence("--ts-policy", "--timestamp-file", (opt_timeStamp != NULL));
+      app.checkValue(cmd.getValue(opt_ts_policyoid));
+      opt_timeStamp->setPolicyOID(opt_ts_policyoid);
+    }
+    cmd.endOptionBlock();
+
+    // output command line options
     cmd.beginOptionBlock();
     if (cmd.findOption("--write-xfer-same")) opt_oxfer = EXS_Unknown;
     if (cmd.findOption("--write-xfer-little")) opt_oxfer = EXS_LittleEndianExplicit;
     if (cmd.findOption("--write-xfer-big")) opt_oxfer = EXS_BigEndianExplicit;
     if (cmd.findOption("--write-xfer-implicit")) opt_oxfer = EXS_LittleEndianImplicit;
     cmd.endOptionBlock();
-
     cmd.beginOptionBlock();
     if (cmd.findOption("--length-explicit")) opt_oenctype = EET_ExplicitLength;
     if (cmd.findOption("--length-undefined")) opt_oenctype = EET_UndefinedLength;
     cmd.endOptionBlock();
-
     if (cmd.findOption("--dump"))
     {
       app.checkDependence("--dump", "--sign or --sign-item", (opt_operation == DSO_sign) || (opt_operation == DSO_signItem));
@@ -1024,141 +744,135 @@ int main(int argc, char *argv[])
       opt_dumpFile = fopen(fileName, "wb");
       if (opt_dumpFile == NULL)
       {
-        OFLOG_FATAL(dcmsignLogger, "unable to create dump file '" << fileName << "'");
-        return 10;
+        DCMSIGN_FATAL("unable to create dump file '" << fileName << "'");
+        result = EXITCODE_CANNOT_WRITE_SUPPORT_FILE;
+        goto cleanup;
       }
     }
   }
-
   /* print resource identifier */
-  OFLOG_DEBUG(dcmsignLogger, rcsid << OFendl);
-
+  DCMSIGN_DEBUG(rcsid << OFendl);
   /* make sure data dictionary is loaded */
   if (!dcmDataDict.isDictionaryLoaded())
   {
-    OFLOG_WARN(dcmsignLogger, "no data dictionary loaded, "
+    DCMSIGN_WARN("no data dictionary loaded, "
       << "check environment variable: " << DCM_DICT_ENVIRONMENT_VARIABLE);
   }
-
-  // open inputfile
+  // open input file
   if ((opt_ifname == NULL) || (strlen(opt_ifname) == 0))
   {
-    OFLOG_FATAL(dcmsignLogger, "invalid filename: <empty string>");
-    return 1;
+    DCMSIGN_FATAL("invalid filename: <empty string>");
+    result = EXITCODE_NO_INPUT_FILES;
+    goto cleanup;
   }
-
-  OFLOG_INFO(dcmsignLogger, "open input file " << opt_ifname);
-
-  DcmFileFormat *fileformat = new DcmFileFormat;
-
-  OFCondition sicond = fileformat->loadFile(opt_ifname, opt_ixfer, EGL_noChange, DCM_MaxReadLength, opt_readMode);
+  DCMSIGN_INFO("open input file " << opt_ifname);
+  sicond = fileformat.loadFile(opt_ifname, opt_ixfer, EGL_noChange, DCM_MaxReadLength, opt_readMode);
   if (sicond.bad())
   {
-    OFLOG_FATAL(dcmsignLogger, sicond.text() << ": reading file: " << opt_ifname);
-    return 1;
+    DCMSIGN_FATAL(sicond.text() << ": reading file: " << opt_ifname);
+    result = EXITCODE_CANNOT_READ_INPUT_FILE;
+    goto cleanup;
   }
-
-  DcmDataset *dataset = fileformat->getDataset();
-
-  SiCertificate cert;
-  SiPrivateKey key;
-
+  dataset = fileformat.getDataset();
   if (opt_certfile)
   {
     sicond = cert.loadCertificate(opt_certfile, opt_keyFileFormat);
     if (sicond != EC_Normal)
     {
-      OFLOG_FATAL(dcmsignLogger, sicond.text() << ": while loading certificate file '" << opt_certfile << "'");
-      return 1;
+      DCMSIGN_FATAL(sicond.text() << ": while loading certificate file '" << opt_certfile << "'");
+      result = EXITCODE_CANNOT_READ_INPUT_FILE;
+      goto cleanup;
     }
   }
-
   if (opt_keyfile)
   {
     if (opt_passwd) key.setPrivateKeyPasswd(opt_passwd);
     sicond = key.loadPrivateKey(opt_keyfile, opt_keyFileFormat);
     if (sicond != EC_Normal)
     {
-      OFLOG_FATAL(dcmsignLogger, sicond.text() << ": while loading private key file '" << opt_keyfile << "'");
-      return 1;
+      DCMSIGN_FATAL(sicond.text() << ": while loading private key file '" << opt_keyfile << "'");
+      result = EXITCODE_CANNOT_READ_INPUT_FILE;
+      goto cleanup;
     }
   }
-
   // need to load all data into memory before signing the document,
   // otherwise the pixel data would be empty for compressed images
-  fileformat->loadAllDataIntoMemory();
-
+  fileformat.loadAllDataIntoMemory();
   // select transfer syntax in which digital signatures are created
   opt_signatureXfer = dataset->getOriginalXfer();
-
   // use Little Endian Explicit for uncompressed files
   if ((opt_signatureXfer == EXS_LittleEndianImplicit) ||
       (opt_signatureXfer == EXS_BigEndianExplicit))
      opt_signatureXfer = EXS_LittleEndianExplicit;
-
   // now do the real work
   switch (opt_operation)
   {
     case DSO_verify:
-      OFLOG_INFO(dcmsignLogger, "verifying all signatures.");
-      result = do_verify(dataset);
-      if (result != 0) return result;
+      DCMSIGN_INFO("verifying all signatures.");
+      result = DcmSignatureHelper::do_verify(dataset, certVerifier, opt_verificationPolicy, opt_timestampPolicy);
+      if (result != 0) goto cleanup;
       break;
     case DSO_sign:
-      OFLOG_INFO(dcmsignLogger, "create signature in main object.");
-      result = do_sign(dataset, key, cert, opt_mac, opt_profile, opt_tagList, opt_signatureXfer, opt_dumpFile);
-      if (result != 0) return result;
+      DCMSIGN_INFO("create signature in main object.");
+      result = DcmSignatureHelper::do_sign(dataset, key, cert, opt_mac, opt_profile, opt_tagList, opt_signatureXfer, opt_dumpFile, opt_sigPurpose, opt_timeStamp);
+      if (result != 0) goto cleanup;
       break;
     case DSO_signItem:
-      OFLOG_INFO(dcmsignLogger, "create signature in sequence item.");
-      result = do_sign_item(dataset, key, cert, opt_mac, opt_profile, opt_tagList, opt_location, opt_signatureXfer, opt_dumpFile);
-      if (result != 0) return result;
+      DCMSIGN_INFO("create signature in sequence item.");
+      result = DcmSignatureHelper::do_sign_item(dataset, key, cert, opt_mac, opt_profile, opt_tagList, opt_location, opt_signatureXfer, opt_dumpFile, opt_sigPurpose, opt_timeStamp);
+      if (result != 0) goto cleanup;
+      break;
+    case DSO_insertTimestamp:
+      DCMSIGN_INFO("inserting certified timestamp.");
+      result = DcmSignatureHelper::do_insert_ts(dataset, opt_timeStamp);
+      if (result != 0) goto cleanup;
       break;
     case DSO_remove:
-      OFLOG_INFO(dcmsignLogger, "removing signature from sequence item.");
-      result = do_remove(dataset, opt_location);
-      if (result != 0) return result;
+      DCMSIGN_INFO("removing signature from sequence item.");
+      result = DcmSignatureHelper::do_remove(dataset, opt_location);
+      if (result != 0) goto cleanup;
       break;
     case DSO_removeAll:
-      OFLOG_INFO(dcmsignLogger, "removing all signatures.");
-      result = do_remove_all(dataset);
-      if (result != 0) return result;
+      DCMSIGN_INFO("removing all signatures.");
+      result = DcmSignatureHelper::do_remove_all(dataset);
+      if (result != 0) goto cleanup;
       break;
   }
-
   if (opt_dumpFile)
   {
     if (0 != fclose(opt_dumpFile))
     {
-      OFLOG_FATAL(dcmsignLogger, "Error while closing dump file, content may be incomplete.");
+      DCMSIGN_FATAL("Error while closing dump file, content may be incomplete.");
     }
     opt_dumpFile = NULL;
   }
-
   if (opt_ofname)
   {
-    OFLOG_INFO(dcmsignLogger, "create output file " << opt_ofname);
-
+    DCMSIGN_INFO("create output file " << opt_ofname);
     if (opt_oxfer == EXS_Unknown) opt_oxfer = dataset->getOriginalXfer();
     DcmXfer opt_oxferSyn(opt_oxfer);
     if (dataset->chooseRepresentation(opt_oxfer, NULL).bad() || (! dataset->canWriteXfer(opt_oxfer)))
     {
-      OFLOG_FATAL(dcmsignLogger, "No conversion to transfer syntax " << opt_oxferSyn.getXferName() << " possible!");
-      return 1;
+      DCMSIGN_FATAL("No conversion to transfer syntax " << opt_oxferSyn.getXferName() << " possible!");
+      result = EXITCODE_CANNOT_WRITE_OUTPUT_FILE;
+      goto cleanup;
     }
-
-    sicond = fileformat->saveFile(opt_ofname, opt_oxfer, opt_oenctype, opt_oglenc, opt_opadenc, OFstatic_cast(Uint32, opt_filepad), OFstatic_cast(Uint32, opt_itempad));
+    sicond = fileformat.saveFile(opt_ofname, opt_oxfer, opt_oenctype, opt_oglenc, opt_opadenc, OFstatic_cast(Uint32, opt_filepad), OFstatic_cast(Uint32, opt_itempad));
     if (sicond.bad())
     {
-      OFLOG_FATAL(dcmsignLogger, sicond.text() << ": writing file: " <<  opt_ofname);
-      return 1;
+      DCMSIGN_FATAL(sicond.text() << ": writing file: " <<  opt_ofname);
+      result = EXITCODE_CANNOT_WRITE_OUTPUT_FILE;
+      goto cleanup;
     }
   }
 
+cleanup:
+
+  delete opt_timeStamp;
   delete opt_mac;
   delete opt_profile;
   delete opt_tagList;
-  return 0;
+  return result;
 }
 
 #else /* WITH_OPENSSL */
@@ -1169,7 +883,7 @@ int main(int, char *[])
        << OFFIS_CONSOLE_APPLICATION " requires the OpenSSL library." << OFendl
        << "This " OFFIS_CONSOLE_APPLICATION " has been configured and compiled without OpenSSL." << OFendl
        << "Please reconfigure your system and recompile if appropriate." << OFendl;
-  return 0;
+  return EXITCODE_NOOPENSSL;
 }
 
 #endif /* WITH_OPENSSL */
index bc3ee3ced77988cc2fc00df3366799be0655c19e..9b4f197b230b0a6409b352e6477ecfed5d994881 100644 (file)
@@ -9,6 +9,7 @@ external OpenSSL library.
 
 The main interface classes are:
 \li \b DcmSignature
+\li \b DcmSignatureHelper
 \li \b SiSecurityProfile
 \li \b SiCertificate
 \li \b SiPrivateKey
@@ -27,33 +28,30 @@ The following example shows how to verify all signatures in a DICOM file:
 DcmFileFormat fileformat;
 if (fileformat.loadFile("test.dcm").good())
 {
-  int counter = 0;          // counts the signatures in the DICOM file
-  int corrupt_counter = 0;  // counts signatures that failed verification
-
-  DcmDataset *dataset = fileformat.getDataset();
-  DcmStack stack;           // stores current location within file
-  DcmSignature signer;      // signature handler
-  DcmItem *sigItem = DcmSignature::findFirstSignatureItem(*dataset, stack);
-  while (sigItem) // browse through items that contain digital signatures
+  // Load a root Certification Authority certificate from "ca_cert.pem"
+  // and declare it as trusted. All certificates issued by this CA will
+  // be considered trustworthy (if within their validity time).
+  SiCertificateVerifier certVerifier;
+  if (certVerifier.addTrustedCertificateFile("ca_cert.pem",
+    X509_FILETYPE_PEM).bad())
   {
-    signer.attach(sigItem); // each item may contain multiple signatures
-    for (unsigned long l=0; l < signer.numberOfSignatures(); ++l)
-    {
-      if (signer.selectSignature(l).good())
-      {
-        ++counter;
-        if (signer.verifyCurrent().bad())  // verify signature
-            corrupt_counter++;
-      }
-    }
-    signer.detach();
-    sigItem = DcmSignature::findNextSignatureItem(*dataset, stack);
+    cerr << "unable to load CA certificate" << endl;
+    return;
   }
-  if (counter == 0)
-      cerr << "no signatures found in dataset." << endl;
+
+  // Verify all signatures in the dataset, and verify the signer
+  // certificate against the root CA defined above.
+  // Fail if no signature is present in the dataset, but do not require
+  // any specific DICOM signature profile. Verify a secure timestamp
+  // if present, but do not fail signature verification if no timestamp
+  // is there.
+  int result = DcmSignatureHelper::do_verify(fileformat.getDataset(),
+    certVerifier, ESVP_requireSignature, ETVP_verifyTSIfPresent);
+
+  if (result == 0)
+    std::cerr << "signature(s) found and successfully verified" << endl;
   else
-      cerr << counter << " signatures verified in dataset, "
-           << corrupt_counter << " corrupted." << endl;
+    std::cerr << "signature absent or verification failed"  << endl;
 }
 \endcode
 
@@ -63,10 +61,19 @@ The following example shows how to sign a DICOM file:
 DcmFileFormat fileformat;
 if (fileformat.loadFile("test.dcm").good())
 {
+  // dataset to be signed
   DcmDataset *dataset = fileformat.getDataset();
-  SiCreatorProfile profile;  // select the "RSA Creator Profile"
+
+  // select transfer syntax in which digital signature will be created
+  E_TransferSyntax xfer = dataset->getOriginalXfer();
+
+  // use Little Endian Explicit for uncompressed files
+  if ((xfer == EXS_LittleEndianImplicit) ||
+      (xfer == EXS_BigEndianExplicit))
+     xfer = EXS_LittleEndianExplicit;
+
+  SiCreatorProfile profile;  // use the "RSA Creator Profile"
   SiRIPEMD160 mac;           // use RIPEMD160 as MAC algorithm
-  DcmSignature signer;       // signature handler
   SiCertificate cert;        // our certificate
   if (cert.loadCertificate("certificate.pem", X509_FILETYPE_PEM).bad())
   {
@@ -79,11 +86,21 @@ if (fileformat.loadFile("test.dcm").good())
     cerr << "unable to load private key" << endl;
     return;
   }
-  signer.attach(dataset); // connect handler to data set
-  if (signer.createSignature(key, cert, mac, profile).good())
-  {
-    fileformat.saveFile("test_signed.dcm");  // write back
-  }
+
+  // list of attributes to be signed. It can remain empty here
+  // since we're using the RSA Creator Profile to determine the
+  // list of attributes that needs to be signed
+  DcmAttributeTag tags;
+
+  // now create the signature
+  int result = DcmSignatureHelper::do_sign(dataset,
+    key, cert, &mac, &profile, &tags, xfer, NULL,
+    SiSignaturePurpose::ESP_none, NULL);
+
+   if (result == 0)
+     std::cerr << "signature successfully created" << endl;
+   else
+     std::cerr << "signature creation failed"  << endl;
 }
 \endcode
 
index 5acae9a730ff9c925401060f6f74a50b2d1a72a2..ceb1766dcc64335aeb37f040ce1d7c1307882515 100644 (file)
@@ -94,6 +94,14 @@ input transfer syntax:
 
   -ti   --read-xfer-implicit
           read with implicit VR little endian TS
+
+handling of defined length UN elements:
+
+  -uc   --retain-un
+          retain elements as UN (default)
+
+  +uc   --convert-un
+          convert to real VR if known
 \endverbatim
 
 \subsection dcmsign_signature_commands signature commands
@@ -107,6 +115,10 @@ input transfer syntax:
   +si   --sign-item  [k]eyfile, [c]ertfile, [i]tem location: string
           create signature in sequence item
 
+  +t    --insert-timestamp  ts[q]file, ts[r]file [u]idfile: string
+          insert certified timestamp from ts response r
+          from timestamp query q at signature UID u
+
   +r    --remove  [s]ignature UID: string
           remove signature
 
@@ -114,7 +126,83 @@ input transfer syntax:
           remove all signatures from data set
 \endverbatim
 
-\subsection dcmsign_signature_creation_options signature creation options (only with --sign or --sign-item):
+\subsection dcmsign_general_signature_options general signature options
+\verbatim
+key and certificate file format:
+
+  -pem  --pem-keys
+          read keys/certificates as PEM file (default)
+
+  -der  --der-keys
+          read keys/certificates as DER file
+
+signature format:
+
+  -fn   --format-new
+          use correct DICOM signature format (default)
+
+  -fo   --format-old
+          use old (pre-3.5.4) DCMTK signature format, non-conformant
+          if signature includes compressed pixel data. This option should
+          only be used to verify signatures in the old format.
+\endverbatim
+
+\subsection dcmsign_signature_verification_options signature verification options (only with --verify)
+\verbatim
+signature verification:
+
+  +rv   --verify-if-present
+          verify signatures if present, pass otherwise
+          (default)
+
+  +rg   --require-sig
+          fail if no signature at all is present
+
+  +rc   --require-creator
+          fail if no creator RSA signature is present
+
+  +ru   --require-auth
+          fail if no auth RSA signature is present
+
+  +rs   --require-sr
+          fail if no SR RSA signature is present
+
+timestamp verification:
+
+  +tv   --verify-ts
+          verify certified timestamp if present (default)
+
+  -tv   --ignore-ts
+          ignore certified timestamps
+
+  +tr   --require-ts
+          fail if no certified timestamp is present
+
+certification authority:
+
+  +cf   --add-cert-file
+          [f]ilename: string
+          add trusted certificate file to cert store
+
+  +uf   --add-ucert-file
+          [f]ilename: string
+          add untrusted intermediate certificate file
+
+  +cd   --add-cert-dir
+          [d]irectory: string
+          add certificates in d to cert store
+
+  +cr   --add-crl-file
+          [f]ilename: string
+          add certificate revocation list file
+          (implies --enable-crl-vfy)
+
+  +cl   --enable-crl-vfy
+          enable certificate revocation list verification
+
+\endverbatim
+
+\subsection dcmsign_signature_creation_options signature creation options (only with --sign or --sign-item)
 \verbatim
 private key password:
 
@@ -127,14 +215,6 @@ private key password:
   -pw   --null-passwd
           use empty string as password
 
-key and certificate file format:
-
-  -pem  --pem-keys
-          read keys/certificates as PEM file (default)
-
-  -der  --der-keys
-          read keys/certificates as DER file
-
 digital signature profile:
 
   -pf   --profile-none
@@ -149,6 +229,12 @@ digital signature profile:
   +pa   --profile-auth
           enforce authorization signature profile
 
+  +pr   --profile-sr
+          enforce SR RSA signature profile
+
+  +pv   --profile-srv
+          enforce SR RSA signature profile (verification)
+
 MAC algorithm:
 
   +mr   --mac-ripemd160
@@ -160,6 +246,27 @@ MAC algorithm:
   +mm   --mac-md5
           use MD 5
 
+  +m2   --mac-sha256
+          use SHA-256
+
+  +m3   --mac-sha384
+          use SHA-384
+
+  +m5   --mac-sha512
+          use SHA-512
+
+signature purpose:
+
+  +lp   --list-purposes
+          show list of signature purpose codes and exit
+
+  -sp   --no-sig-purpose
+          do not add signature purpose (default)
+
+  +sp   --sig-purpose
+          [p]urpose code: integer (1..18)
+          add digital signature purpose code p
+
 tag selection:
 
   -t    --tag
@@ -170,14 +277,61 @@ tag selection:
   -tf   --tag-file  [f]ilename: string
           read list of tags from text file
 
-signature format:
+\endverbatim
 
-  -fn   --format-new
-          use correct DICOM signature format (default)
+\subsection dcmsign_timestamp_creation_options timestamp creation options (only with --sign or --sign-item)
+\verbatim
+timestamp creation:
 
-  -fo   --format-old
-          use old (pre-3.5.4) DCMTK signature format, non-conformant
-          if signature includes compressed pixel data
+  -ts   --timestamp-off
+          do not create timestamp (default)
+
+  +ts   --timestamp-file  [t]sq-filename, [u]id-filename: string
+          create timestamp query file t and uid file u
+
+timestamp MAC algorithm (only with --timestamp-file):
+
+  +tm2  --ts-mac-sha256
+          use SHA-256 (default)
+
+  +tm3  --ts-mac-sha384
+          use SHA-384
+
+  +tm5  --ts-mac-sha512
+          use SHA-512
+
+  +tmr  --ts-mac-ripemd160
+          use RIPEMD 160
+
+  +tms  --ts-mac-sha1
+          use SHA-1 (not recommended)
+
+  +tmm  --ts-mac-md5
+          use MD5 (not recommended)
+
+timestamp query nonce options (only with --timestamp-file):
+
+  +tn   --ts-use-nonce
+          include random nonce (default)
+
+  -tn   --ts-no-nonce
+          do not include nonce
+
+timestamp certificate inclusion options (only with --timestamp-file):
+
+  +tc   --ts-request-cert
+          request TSA certificate in timestamp (default)
+
+  -tc   --ts-no-cert
+          do not request TSA certificate in timestamp
+
+timestamp policy options (only with --timestamp-file):
+
+  -tp   --ts-no-policy
+          do not specify ts policy (default)
+
+  +tp   --ts-policy  [p]olicy-OID: string
+          request timestamp policy p
 \endverbatim
 
 \subsection dcmsign_output_options output options
@@ -219,21 +373,24 @@ The \b dcmsign utility reads and writes a number of files and file formats
 which are described in this section.
 
 Public Key Certificates are expected in X.509v3 format, either with PEM or DER
-encoding. The dcmsign utility currently supports RSA and DSA public keys,
+encoding.  The \b dcmsign utility currently supports RSA and DSA public keys,
 although only RSA keys are defines in the Security Profiles of the DICOM
 standard.
 
 Private Keys are expected in PEM or DER encoding. PEM is recommended (and
-default) because this allows one to keep private keys in encrypted form. Command
-line options control the behavior of \b dcmsign when an encrypted PEM key is
-opened (see above).  In general it is not recommended to specify the encryption
-password in the command line because the command line may be visible to other
-processes in the system, e.g. "ps -ef".
+default) because this allows one to keep private keys in encrypted form.
+Command line options control the behavior of \b dcmsign when an encrypted PEM
+key is opened (see above).  In general it is not recommended to specify the
+encryption password in the command line because the command line may be visible
+to other processes in the system, e.g. "ps -ef".
 
-The list of data elements to sign can either be read from a file or specified
-on the command line or both (in this case the keys are combined).
+By default, \b dcmsign will create a signature covering all data elements in the
+dataset or item. This default can be overridden by explicitly specifying a list
+of data elements (attribute tags).  This list can either be read from a file or
+specified on the command line or both (in this case the attribute tags are
+combined).
 
-On the command line, attribute keys are specified as
+On the command line, attribute tags are specified as
 
 \verbatim
 --tag "gggg,eeee"  where gggg and eeee are the hexadecimal group
@@ -243,9 +400,13 @@ On the command line, attribute keys are specified as
 \endverbatim
 
 When attribute tags are read from file with the \e --tag-file option, a plain
-text file of max. 64 kbyte is expected.  Tags within the file are either
-symbolic names from the data dictionary or have the format (gggg,eeee) (with
-braces).  Tags are separated by one or more whitespace characters.
+text file is expected.  Tags within the file are either symbolic names from the
+data dictionary or have the format (gggg,eeee) (with braces).  Tags are
+separated by one or more whitespace characters.
+
+The currently selected digital signature profile may specify additional
+attribute tags required to be included in the signature, which will be silently
+added.
 
 The \e --sign-item operation requires a location string that describes in which
 sequence item a signature is to be created.  The location string has the
@@ -269,6 +430,52 @@ ReferencedImageSequence (0008,1140) which is located in the first item of the
 ReferencedSeriesSequence (0008,1115) which is located in the main DICOM
 dataset.
 
+\subsection dcmsign_certified_timestamps Certified Timestamps
+
+Starting with release 3.6.6, \b dcmsign offers support for certified timestamps
+according to RFC 3161.  For now, the tool does not implement any of the network
+protocols defined in RFC 3161 for communicating with a timestamp authority
+(TSA), but it can write a timestamp query (TSQ) during signature creation, and
+the new command \e --insert-timestamp will read a timestamp response (TSR) from
+file and add it to the DICOM digital signature. Since a DICOM file can contain
+multiple signatures, a "UID file" (which contains the Digital Signature UID)
+is used to identify the signature to which the TSR should be added.  The
+\b dcmsign tool will also perform various consistency checks before storing the
+timestamp.
+
+During signature verification, the presence of a certified timestamp will be
+detected and the timestamp will also be verified unless option \e --ignore-ts
+was used.  Signature verification and timestamp verification use a common
+certificate store to check the certificates of the DICOM signature and the
+timestamp.  This store can be populated with the options \e --add-cert-file and
+\e --add-cert-dir, which both add trusted CA certificates, \e --add-ucert-file,
+which adds an untrusted intermediate CA certificate, and \e --add-crl-file,
+which adds a certificate revocation list.
+
+\subsection dcmsign_hashed_certificate_directories Hashed Certificate Directories
+
+Instead of adding CA certificates and certificate revocation lists (CRLs)
+manually using \e --add-cert-file and \e --add-crl-file, the user can set-up
+a directory where \b dcmsign will look-up and load certificates and CRLs from
+as needed, using \e --add-cert-dir.
+
+Th directory should contain one certificate or CRL per file in PEM format,
+with a filename of the form hash.N for a certificate, or hash.rN for a CRL.
+The hash is the value returned by
+
+  <em>openssl x509 -hash -noout -in \<filename.pem\></em> (for a certificate)
+  <em>openssl crl -hash -noout -in \<filename.pem\></em> (for a CRL)
+
+The .N or .rN suffix is a sequence number that starts at zero, and is
+incremented consecutively for each certificate or CRL with the same hash value.
+Gaps in the sequence numbers are not supported, it is assumed that there are no
+more objects with the same hash beyond the first missing number in the sequence.
+
+CRLs will only be verified when option \e --enable-crl-vfy is specified.  In
+this case, \b dcmsign will expect a CRL to be present for each CA and will fail
+signature verification if no CRL can be found for the CA that issued the signer
+certificate.
+
 \section dcmsign_logging LOGGING
 
 The level of logging output of the various command line tools and underlying
@@ -310,6 +517,53 @@ allows one to summarize common combinations of options/parameters and avoids
 longish and confusing command lines (an example is provided in file
 <em>\<datadir\>/dumppat.txt</em>).
 
+\section dcmsign_exit_codes EXIT CODES
+
+The \b dcmsign utility uses the following exit codes when terminating.  This
+enables the user to check for the reason why the application terminated.
+
+\subsection dcmsign_exit_codes_general general
+\verbatim
+EXITCODE_NO_ERROR                         0
+EXITCODE_COMMANDLINE_SYNTAX_ERROR         1
+EXITCODE_NOOPENSSL                        5
+\endverbatim
+
+\subsection dcmsign_exit_codes_input_file_errors input file errors
+\verbatim
+EXITCODE_CANNOT_READ_INPUT_FILE          20
+EXITCODE_NO_INPUT_FILES                  21
+EXITCODE_CANNOT_READ_TAG_FILE            30
+EXITCODE_CANNOT_READ_TSQ_FILE            31
+EXITCODE_CANNOT_READ_TSR_FILE            32
+EXITCODE_CANNOT_READ_UID_FILE            33
+\endverbatim
+
+\subsection dcmsign_exit_codes_output_file_errors output file errors
+\verbatim
+EXITCODE_CANNOT_WRITE_OUTPUT_FILE        40
+EXITCODE_CANNOT_WRITE_SUPPORT_FILE       46
+\endverbatim
+
+\subsection dcmsign_exit_codes_processing_errors processing errors
+\verbatim
+EXITCODE_CANNOT_ACCESS_SIGNATURE         80
+EXITCODE_CANNOT_ACCESS_TS                81
+EXITCODE_CANNOT_INSERT_TS                82
+EXITCODE_SIGNATURE_REMOVAL_FAILED        83
+EXITCODE_SIGNATURE_UID_NOT_FOUND         84
+EXITCODE_SIGNATURE_CREATION_FAILED       85
+EXITCODE_SYNTAX_ERROR_IN_TAG_FILE        86
+EXITCODE_TS_CONSISTENCY_CHECK_FAILED     87
+\endverbatim
+
+\subsection dcmsign_exit_codes_application_errors application specific errors
+\verbatim
+EXITCODE_NO_SIGNATURES_PRESENT           100
+EXITCODE_SIGNATURE_VERIFICATION_FAILED   101
+EXITCODE_SIGNATURE_VERIFICATION_POLICY   102
+\endverbatim
+
 \section dcmsign_environment ENVIRONMENT
 
 The \b dcmsign utility will attempt to load DICOM data dictionaries specified
@@ -328,6 +582,6 @@ It is an error if no data dictionary can be loaded.
 
 \section dcmsign_copyright COPYRIGHT
 
-Copyright (C) 2000-2014 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 2000-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
diff --git a/dcmsign/include/dcmtk/dcmsign/dcsighlp.h b/dcmsign/include/dcmtk/dcmsign/dcsighlp.h
new file mode 100644 (file)
index 0000000..f253a91
--- /dev/null
@@ -0,0 +1,222 @@
+/*
+ *
+ *  Copyright (C) 1998-2019, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmsign
+ *
+ *  Author: Marco Eichelberg
+ *
+ *  Purpose:
+ *    classes: DcmSignatureHelper
+ *
+ */
+
+#ifndef DCMSIGHLP_H
+#define DCMSIGHLP_H
+
+#include "dcmtk/config/osconfig.h"
+#include "dcmtk/ofstd/oftypes.h"     /* for Uint32 */
+#include "dcmtk/ofstd/ofstring.h"    /* for class OFString */
+#include "dcmtk/dcmdata/dcxfer.h"    /* for E_TransferSyntax */
+#include "dcmtk/dcmsign/sidefine.h"  /* for DCMTK_DCMSIGN_EXPORT */
+#include "dcmtk/dcmsign/sipurpos.h"  /* for class SiSignaturePurpose */
+#include "dcmtk/dcmsign/sitypes.h"   /* for dcmsign enums */
+
+#ifdef WITH_OPENSSL
+
+class DcmAttributeTag;
+class DcmItem;
+class DcmStack;
+class DcmTagKey;
+class SiCertificate;
+class SiMAC;
+class SiPrivateKey;
+class SiSecurityProfile;
+class SiTimeStamp;
+class SiTimeStampFS;
+class SiCertificateVerifier;
+class DcmSignature;
+
+/** this class provides helper functions for creating and verifying
+ *  digital signatures. It encapsulates most of the code that was part
+ *  of the main command line program "dcmsign" in prior DCMTK releases.
+ *  @remark this class is only available if DCMTK is compiled with
+ *  OpenSSL support enabled.
+ */
+class DCMTK_DCMSIGN_EXPORT DcmSignatureHelper
+{
+public:
+
+  /// default constructor
+  DcmSignatureHelper();
+
+  /// destructor
+  virtual ~DcmSignatureHelper();
+
+  /** locate a specific item within the given dataset.
+   * @param dataset dataset to be searched
+   * @param location location string. Format is "sequence[item]{.sequence[item]}*"
+   *   Where sequence can be (gggg,eeee) or a dictionary name and items
+   *   within sequences are counted from zero.
+   * @return pointer to the item searched if found, NULL otherwise
+   */
+  static DcmItem *locateItemforSignatureCreation(DcmItem& dataset, const char *location);
+
+  /** read a list of attributes from a text file.
+   * The attributes can be in the form (gggg,eeee) or can be dictionary names,
+   * separated by arbitrary whitespace.
+   * @param filename file to be read from
+   * @param tagList attribute tags are added to this list
+   * @return 0 if successful, a program exit code otherwise
+   */
+  static int parseTextFile(const char *filename, DcmAttributeTag& tagList);
+
+  /** read an attribute tag in the form "gggg,eeee" and adds it
+   * to the given attribute tag list
+   * @param c input string
+   * @param tagList list to be added to
+   * @return true if successful, false otherwise
+   */
+  static OFBool addTag(const char *c, DcmAttributeTag& tagList);
+
+  /** print the location stack into the given stack.
+   * It is assumed that the stack top is a DigitalSignatureSequence which is not printed
+   * and that the stack bottom is the main dataset, which is also not printed.
+   * @param stack search stack, as returned by DcmSignature::findFirstSignatureItem() etc.
+   * @param str printable text returned in this string.
+   */
+  static void printSignatureItemPosition(DcmStack& stack, OFString& str);
+
+  /** perform a signature operation on a given dataset
+   * @param dataset to sign
+   * @param key private key for signature
+   * @param cert certificate for signature
+   * @param opt_mac MAC for signature
+   * @param opt_profile security profile for signature
+   * @param opt_tagList list of attribute tags, may be NULL
+   * @param opt_signatureXfer signature transfer syntax
+   * @param dumpFile file to dump the byte stream to
+   * @param opt_sigPurpose signature purpose
+   * @param timeStamp pointer to timestamp client, may be NULL
+   * @return 0 if successful, a program exit code otherwise
+   */
+  static int do_sign(
+    DcmItem *dataset,
+    SiPrivateKey& key,
+    SiCertificate& cert,
+    SiMAC *opt_mac,
+    SiSecurityProfile *opt_profile,
+    DcmAttributeTag *opt_tagList,
+    E_TransferSyntax opt_signatureXfer,
+    FILE *dumpFile,
+    SiSignaturePurpose::E_SignaturePurposeType opt_sigPurpose,
+    SiTimeStamp *timeStamp = NULL);
+
+  /** performs a signature operation on a sub-item within a dataset
+   * @param dataset in which to sign
+   * @param key private key for signature
+   * @param cert certificate for signature
+   * @param opt_mac MAC for signature
+   * @param opt_profile security profile for signature
+   * @param opt_tagList list of attribute tags, may be NULL
+   * @param location location string. Format is "sequence[item]{.sequence[item]}*"
+   *   Where sequence can be (gggg,eeee) or a dictionary name and items
+   *   within sequences are counted from zero.
+   * @param opt_signatureXfer signature transfer syntax
+   * @param dumpFile file to dump the byte stream to
+   * @param opt_sigPurpose signature purpose
+   * @param timeStamp pointer to timestamp client, may be NULL
+   * @return 0 if successful, a program exit code otherwise
+   */
+  static int do_sign_item(
+    DcmItem *dataset,
+    SiPrivateKey& key,
+    SiCertificate& cert,
+    SiMAC *opt_mac,
+    SiSecurityProfile *opt_profile,
+    DcmAttributeTag *opt_tagList,
+    const char *opt_location,
+    E_TransferSyntax opt_signatureXfer,
+    FILE *dumpFile,
+    SiSignaturePurpose::E_SignaturePurposeType opt_sigPurpose,
+    SiTimeStamp *timeStamp = NULL);
+
+  /** verify all signatures in the given dataset and print results to stdout.
+   * @param dataset dataset to verify
+   * @param certVerifier certification verifier helper object
+   * @param verificationPolicy signature verification policy
+   * @param timstampPolicy timestamp verification policy
+   * @return 0 if successful, a program exit code otherwise
+   */
+  static int do_verify(
+    DcmItem *dataset,
+    SiCertificateVerifier& certVerifier,
+    E_SignatureVerificationPolicy verificationPolicy,
+    E_TimestampVerificationPolicy timstampPolicy);
+
+  /** insert certified timestamp from file.
+   *  @param dataset in which to add timestamp
+   *  @param timeStamp handler, must not be NULL
+   */
+  static int do_insert_ts(DcmItem *dataset, SiTimeStampFS *timeStamp);
+
+  /** remove all signatures from the given dataset, print action details.
+   * @param dataset dataset to modify
+   * @return 0 if successful, a program exit code otherwise
+   */
+  static int do_remove_all(DcmItem *dataset);
+
+  /** remove the signature with the given UID from the dataset, print action details.
+   * @param dataset dataset to modify
+   * @param opt_location Digital Signature UID of the signature to remove
+   * @return 0 if successful, a program exit code otherwise
+   */
+  static int do_remove(
+    DcmItem *dataset,
+    const char *opt_location);
+
+private:
+
+  /** scans a token from the given string and returns it. Ignores leading whitespace.
+   * @param c string to parse
+   * @param pos position within string, modified after successful scan
+   * @param key tag key returned in this parameter if return value is "tag key".
+   * @param idx index returned in this parameter if return value is "index".
+   * @return -1 for "EOF", 0 for "parse error", 1 for "tag key", 2 for "index", 3 for "period"
+   */
+  static int readNextToken(const char *c, int& pos, DcmTagKey& key, Uint32& idx);
+
+  /** reads a complete text file (max 64K) into a memory block
+   * and returns a pointer to the memory block.
+   * memory must be freed by caller.
+   * @param filename file to be read
+   * @return pointer to memory block if successful, NULL otherwise.
+   */
+  static char *readTextFile(const char *filename);
+
+  /** print the details of the current signature to the logger
+   *  @param sig signature object
+   *  @param stack position of the signature object in the dataset
+   *  @param count number of the signature (counter)
+   */
+  static void printSignatureDetails(DcmSignature& sig, DcmStack& stack, int count);
+
+  /** print the details of the timestamp for the current signature to the logger
+   *  @param sig signature object
+   *  @param tsPolicy timestamp verification policy
+   */
+  static void printTimestampDetails(DcmSignature& sig, E_TimestampVerificationPolicy tsPolicy);
+
+};
+
+#endif
+#endif
index 9da04117d689623e30049a56623547717666d1ea..114029b7dfe3b2c9b75662d038b8f1890028d700 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define DCMSIGN_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/sitypes.h"
 
 #ifdef WITH_OPENSSL
 
-#include "dcmtk/dcmdata/dcxfer.h"  /* for E_TransferSyntax */
+#include "dcmtk/dcmsign/sitypes.h"
+#include "dcmtk/dcmdata/dcxfer.h"    /* for E_TransferSyntax */
+#include "dcmtk/dcmsign/sipurpos.h"  /* for E_SignaturePurposeType */
 
 #define INCLUDE_CSTDIO
 #include "dcmtk/ofstd/ofstdinc.h"
 
+class DcmAttributeTag;
+class DcmDateTime;
 class DcmItem;
-class DcmStack;
 class DcmSequenceOfItems;
-class DcmAttributeTag;
+class DcmStack;
+class DcmTagKey;
 class SiPrivateKey;
 class SiCertificate;
 class SiSecurityProfile;
 class SiMAC;
 class SiTimeStamp;
 
-/** this class provides the main interface to the dcmsign module - it allows 
- *  to create, examine and verify digital signatures in DICOM datasets or 
- *  items. The methods in this class do not handle digital signatures 
- *  embedded in sequence items within the dataset, other than providing 
- *  helper functions that allow to locate and attach the sub-items 
+/** this class provides the main interface to the dcmsign module - it allows
+ *  to create, examine and verify digital signatures in DICOM datasets or
+ *  items. The methods in this class do not handle digital signatures
+ *  embedded in sequence items within the dataset, other than providing
+ *  helper functions that allow to locate and attach the sub-items
  *  separately.
  *  @remark this class is only available if DCMTK is compiled with
  *  OpenSSL support enabled.
@@ -63,18 +66,18 @@ public:
 
   /// default constructor
   DcmSignature();
+
   /// destructor
   virtual ~DcmSignature();
 
   /** attaches a DICOM dataset or item to the signature object.
    *  The dataset is detached by a call to detach() or by destruction
-   *  of the signature object.  This object may modify but never deletes 
+   *  of the signature object.  This object may modify but never deletes
    *  an attached dataset.
    *  @param dataset dataset or item to be attached
    */
-  void attach(DcmItem *dataset);  
-  
+  void attach(DcmItem *dataset);
+
   /** detaches an attached DICOM dataset from the signature object.
    */
   void detach();
@@ -94,18 +97,20 @@ public:
    *    i.e. all signable attributes in the data set are signed.
    *  @param timeStamp pointer to time stamp client used to create timestamps
    *    for the digital signature.
+   *  @param sigPurpose digital signature purpose
    *  @return status code
    */
   OFCondition createSignature(
-    SiPrivateKey& key, 
-    SiCertificate& cert, 
+    SiPrivateKey& key,
+    SiCertificate& cert,
     SiMAC& mac,
-    SiSecurityProfile& profile, 
+    SiSecurityProfile& profile,
     E_TransferSyntax xfer=EXS_LittleEndianExplicit,
     const DcmAttributeTag *tagList=NULL,
-    SiTimeStamp *timeStamp=NULL);
+    SiTimeStamp *timeStamp=NULL,
+    SiSignaturePurpose::E_SignaturePurposeType sigPurpose=SiSignaturePurpose::ESP_none);
 
-  /** returns the number of signatures in the dataset. Does not count 
+  /** returns the number of signatures in the dataset. Does not count
    *  signatures embedded in sequence items within the dataset.
    */
   unsigned long numberOfSignatures();
@@ -121,7 +126,7 @@ public:
    *  @return status code
    */
   OFCondition selectSignature(unsigned long i);
-  
+
   /** verifies the current signature.
    *  Current signature must be selected with selectSignature().
    *  @return SI_EC_Normal if signature is complete and valid, an error code
@@ -166,6 +171,13 @@ public:
    */
   OFCondition getCurrentSignatureDateTime(OFString& str);
 
+  /** returns a pointer to the object representing Signature Date/Time
+   *  of the current signature.
+   *  Current signature must be selected with selectSignature().
+   *  @return pointer to signature datetime if present, NULL otherwise
+   */
+  DcmDateTime *getCurrentSignatureDateTime();
+
   /** returns the Data Elements Signed attribute of the current signature if present.
    *  Current signature must be selected with selectSignature().
    *  If a valid signature is selected but the signature does not contain
@@ -176,13 +188,45 @@ public:
    */
   OFCondition getCurrentDataElementsSigned(DcmAttributeTag& desig);
 
+  /** returns the signature purpose code of the current signature if present.
+   *  Current signature must be selected with selectSignature().
+   *  If a valid signature is selected but the signature does not contain
+   *  a valid SignaturePurposeCodeSequence, this method returns an error code.
+   *  @param codeValue signature purpose code value returned in this parameter upon success
+   *  @param codeMeaning signature purpose code meaning returned in this parameter upon success
+   *  @param codingSchemeDesignator signature purpose coding scheme designator returned in this parameter upon success
+   *  @return status code
+   */
+  OFCondition getCurrentSignaturePurpose(OFString& codeValue, OFString& codeMeaning, OFString& codingSchemeDesignator);
+
+  /** verifies whether the currently selected signature within the
+   *  currently attached dataset matches the requirements of the
+   *  given signature profile.
+   *  @param sprof security profile
+   *  @return EC_Normal if signature matches, an error code otherwise
+   */
+  OFCondition verifySignatureProfile(SiSecurityProfile &sprof);
+
   /** returns the certificate of the current signature if present.
    *  Current signature must be selected with selectSignature().
    *  May return NULL if certificate is unavailable.
    *  @return pointer to current certificate, NULL if unavailable.
    */
   SiCertificate *getCurrentCertificate();
-  
+
+  /** returns the certified timestamp of the current signature if present.
+   *  Current signature must be selected with selectSignature().
+   *  May return NULL if timestamp is unavailable.
+   *  @return pointer to current timestamp, NULL if unavailable.
+   */
+  SiTimeStamp *getCurrentTimestamp();
+
+  /** returns the item of the DigitalSignaturesSequence selected by the last call
+   *  to selectSignature(), or NULL if no signature has been selected.
+   *  @return pointer to current signature item, may be NULL
+   */
+  DcmItem *getSelectedSignatureItem();
+
   /** dump all data that is fed into the MAC algorithm into the given file,
    *  which must be opened and closed by caller.
    *  @param f pointer to file already opened for writing; may be NULL.
@@ -190,7 +234,7 @@ public:
   void setDumpFile(FILE *f);
 
   /** recursively browses through the given dataset and searches the first
-   *  occurence of the DigitalSignaturesSequence. If found, returns
+   *  occurrence of the DigitalSignaturesSequence. If found, returns
    *  a pointer to the Item in which the sequence is contained.
    *  @param item dataset to be browsed
    *  @param stack search stack, must be passed to findNextSignatureItem() later on.
@@ -199,7 +243,7 @@ public:
   static DcmItem *findFirstSignatureItem(DcmItem& item, DcmStack& stack);
 
   /** recursively browses through the given dataset and searches the next
-   *  occurence of the DigitalSignaturesSequence. If found, returns
+   *  occurrence of the DigitalSignaturesSequence. If found, returns
    *  a pointer to the Item in which the sequence is contained.
    *  @param item dataset to be browsed
    *  @param stack search stack as returned by findFirstSignatureItem() or the last call to this method.
@@ -207,6 +251,16 @@ public:
    */
   static DcmItem *findNextSignatureItem(DcmItem& item, DcmStack& stack);
 
+  /** check a DER encoded ASN.1 SEQUENCE structure for a possible pad byte
+   *  and, if a pad byte is detected, remove it by decreasing buflen.
+   *  This will work for SEQUENCEs with one byte and two byte encoding
+   *  (i.e. max 64 kBytes).
+   *  @param buf pointer to DER encoded ASN.1 data
+   *  @param buflen length of buffer pointed to, in bytes. The variable is
+   *    decreased by one if a pad byte is detected.
+   */
+  static void adjustASN1SequenceLength(const unsigned char *buf, unsigned long& buflen);
+
 private:
 
   /// private undefined copy constructor
@@ -225,13 +279,31 @@ private:
    *  @return status code
    */
   OFCondition allocateMACID(Uint16& newID);
-  
+
   /** searches a given item for the DCM_MACIDnumber element and returns
-   *  its value if present, otherwise returns 0.
+   *  its value if present
    *  @param item item to be searched
-   *  @return MAC ID number in item or zero if absent.
+   *  @param macid MAC ID returned in this parameter upon success
+   *  @return EC_Normal if successful, an error code otherwise
    */
-  static Uint16 getMACIDnumber(DcmItem &item);
+  static OFCondition getMACIDnumber(DcmItem &item, Uint16& macid);
+
+  /** checks if all tags from tagList are present in tagListOut,
+   *  which is the list of attribute tags actually included in a signature,
+   *  including tags added due to a signature profile, and without tags
+   *  that were absent in the dataset.
+   *  @param tagList list of attribute tags that should be present in the signature, may be NULL
+   *  @param tagListOut list of attribute tags actually present in the signature, must not be NULL
+   *  @return EC_Normal if check succeeds, an error code otherwise
+   */
+  static OFCondition checkListOfSignedTags(const DcmAttributeTag *tagList, const DcmAttributeTag *tagListOut);
+
+  /** checks if the given tag key is present in tagList
+   *  @param tag tag key
+   *  @param tagList list of tag keys
+   *  @return OFTrue of tag is present in tagList, OFFalse otherwise
+   */
+  static OFBool inTagList(const DcmTagKey &tag, const DcmAttributeTag& tagList);
 
   /** returns the current date and time as a DICOM DT string.
    *  @param str date/time returned in this string.
@@ -257,8 +329,10 @@ private:
   DcmItem *selectedMacParametersItem;
 
   /// pointer to certificate for currently selected signature item
-  SiCertificate *selectedCertificate;  
-  
+  SiCertificate *selectedCertificate;
+
+  /// pointer to certified timestamp for currently selected signature item
+  SiTimeStamp *selectedTimestamp;
 };
 
 #endif
index 2b3d39acdca7f1d4cda933e7229ad7950f02bec8..df9adfb646fcc83ba086ae019e43ab1211c399ee 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define SIALGO_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/sitypes.h"
 
 #ifdef WITH_OPENSSL
 
+#include "dcmtk/dcmsign/sitypes.h"
 #include "dcmtk/ofstd/oftypes.h"
 
 /** 
index 9f37e834214b5280ce25f0ab8adfa4dff01044ff..3c74e8a064091e20cddde8437013b129f2fefb22 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define SIAUTOPR_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/sibrsapr.h"   /* for SiBaseRSAProfile */
 
 #ifdef WITH_OPENSSL
 
+#include "dcmtk/dcmsign/sibrsapr.h"   /* for SiBaseRSAProfile */
+
 /** Authorization Digital Signature Profile
  *  @remark this class is only available if DCMTK is compiled with
  *  OpenSSL support enabled.
@@ -37,17 +38,44 @@ class DCMTK_DCMSIGN_EXPORT SiAuthorizationProfile: public SiBaseRSAProfile
 public:
 
   /// default constructor
-  SiAuthorizationProfile() { }
+  SiAuthorizationProfile();
 
   /// destructor
   virtual ~SiAuthorizationProfile() { }
 
   /** checks whether an attribute with the given tag is required to be signed
-   *  for the current security profile.
+   *  for the current security profile if the attribute is present in the dataset
    *  @param key tag key to be checked
    *  @return true if required, false otherwise.
    */
-  virtual OFBool attributeRequired(const DcmTagKey& key) const;
+  virtual OFBool attributeRequiredIfPresent(const DcmTagKey& key) const;
+
+  /** checks whether all attributes that are required unconditionally
+   *  to be signed in this profile are included in the given tagList.
+   *  @param taglist attribute tag list
+   *  @return true if requirements for profile are fulfilled, false otherwise.
+   */
+  virtual OFBool checkRequiredAttributeList(DcmAttributeTag& tagList) const;
+
+  /** some digital signature profiles specify conditions under which certain
+   *  attributes must be included into the signature.
+   *  This method allows the signature profile to inspect the dataset in order
+   *  to determine whether or not the conditions are met.
+   *  This method should be called before DcmSignature::createSignature() is executed.
+   *  @param item the dataset or item to which the signature will be added
+   *  @return status code
+   */
+  virtual OFCondition inspectSignatureDataset(DcmItem &item);
+
+  /** returns true if this signature profile only applies to main dataset level
+   *  @return OFTrue if this signature profile only applies to main dataset level, OFFalse otherwise
+   */
+  virtual OFBool mainDatasetRequired() const;
+
+private:
+
+  /// flag indicating whether or not the signature dataset contains the raw data module
+  OFBool containsRawData_;
 
 };
 
index 423e9b339813defde0cb5450ecf970debceb69a5..0ad911e27246ea44e5c6f3ad12b6577ffaf976d4 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define SIBRSAPR_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/sisprof.h"   /* for SiSecurityProfile */
 
 #ifdef WITH_OPENSSL
 
+#include "dcmtk/dcmsign/sisprof.h"   /* for SiSecurityProfile */
+
 /** Base RSA Digital Signature Profile
  *  @remark This class is only available if DCMTK is compiled with
  *  OpenSSL support enabled.
@@ -41,7 +42,7 @@ public:
 
   /// destructor
   virtual ~SiBaseRSAProfile() { }
-  
+
   /** checks whether the given MAC type can be used with this security profile.
    *  @param macType MAC type to be checked
    *  @return true if MAC type is allowable for this profile, false otherwise.
@@ -61,11 +62,18 @@ public:
   virtual OFBool isAllowableTransferSyntax(E_TransferSyntax xfer) const;
 
   /** checks whether an attribute with the given tag is required to be signed
-   *  for the current security profile.
+   *  for the current security profile if the attribute is present in the dataset
    *  @param key tag key to be checked
    *  @return true if required, false otherwise.
    */
-  virtual OFBool attributeRequired(const DcmTagKey& key) const;
+  virtual OFBool attributeRequiredIfPresent(const DcmTagKey& key) const;
+
+  /** checks whether all attributes that are required unconditionally
+   *  to be signed in this profile are included in the given tagList.
+   *  @param taglist attribute tag list
+   *  @return true if requirements for profile are fulfilled, false otherwise.
+   */
+  virtual OFBool checkRequiredAttributeList(DcmAttributeTag& tagList) const;
 
   /** checks whether an attribute with the given tag must not be signed
    *  for the current security profile.
@@ -74,6 +82,21 @@ public:
    */
   virtual OFBool attributeForbidden(const DcmTagKey& key) const;
 
+  /** some digital signature profiles specify conditions under which certain
+   *  attributes must be included into the signature.
+   *  This method allows the signature profile to inspect the dataset in order
+   *  to determine whether or not the conditions are met.
+   *  This method should be called before DcmSignature::createSignature() is executed.
+   *  @param item the dataset or item to which the signature will be added
+   *  @return status code
+   */
+  virtual OFCondition inspectSignatureDataset(DcmItem &item);
+
+  /** returns true if this signature profile only applies to main dataset level
+   *  @return OFTrue if this signature profile only applies to main dataset level, OFFalse otherwise
+   */
+  virtual OFBool mainDatasetRequired() const;
+
 };
 
 #endif
index c587f30b4d6f36c7c2ecba79875ab3a6902254a5..4aefc687ef5834f5888f6e686d9df76e464325a5 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define SICERT_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/sitypes.h"
 
 #ifdef WITH_OPENSSL
 
+#include "dcmtk/dcmsign/sitypes.h"
 #include "dcmtk/ofstd/ofstring.h"   /* for class OFString */
 
 class DcmItem;
 class SiAlgorithm;
+class OFDateTime;
 struct x509_st;
+struct asn1_string_st;
 typedef struct x509_st X509;
+typedef struct asn1_string_st ASN1_STRING;
+typedef struct asn1_string_st ASN1_GENERALIZEDTIME;
 
 /** a class representing X.509 public key certificates.
  *  @remark this class is only available if DCMTK is compiled with
  *  OpenSSL support enabled.
  */
 class DCMTK_DCMSIGN_EXPORT SiCertificate
-{    
+{
 public:
 
   /// default constructor
   SiCertificate();
-  
+
+  /** constructor
+   *  @param cert pointer to OpenSSL X509 object. Ownership is transferred to the SiCertificate instance
+   */
+  SiCertificate(X509 *cert);
+
   ///destructor
   virtual ~SiCertificate();
 
@@ -69,11 +78,11 @@ public:
    *  @return dcmdata OFCondition status code
    */
   OFCondition write(DcmItem& item);
-  
+
   /** returns the type of public key stored in this certificate
    */
   E_KeyType getKeyType();
-  
+
   /** creates an SiAlgorithm object for the public key contained in this certificate.
    *  If no certificate loaded or operation fails, returns NULL.
    *  New SiAlgorithm object must be deleted by caller.
@@ -124,11 +133,72 @@ public:
    */
   long getCertKeyBits();
 
-  /** returns a pointer to the raw certificate structure or NULL if no 
+  /** returns the name of the elliptic curve used in the certificate.
+   *  @return NULL if the certificate is not of elliptic curve type,
+   *    "unnamed curve" if the curve name has not been stored in the certificate,
+   *    or the short name of the elliptic curve if available.
+   */
+  const char *getCertCurveName();
+
+  /** checks if the length of the public key in the certificate is too short
+   *  and must be considered weak. Currently, an RSA or DSA key with less than
+   *  1024 bits and an ECDSA key with less than 256 bits are considered weak.
+   *  @return OFTrue if key is weak, OFFalse otherwise.
+   */
+  OFBool isWeakKey();
+
+  /** checks if the length of the public key in the certificate is too short
+   *  and must be considered weak, and if so, prints a warning to the logger.
+   */
+  void checkForWeakKey();
+
+  /** returns a pointer to the raw certificate structure or NULL if no
    *  certificate present. Should not be called by users of this library.
    */
   X509 *getRawCertificate();
 
+  /** returns true if the certificate expires before the given date.
+   *  @param date a string in the format YYMMDDHHMMSSZ or YYYYMMDDHHMMSSZ
+   *    (where Z represents the letter 'Z', meaning time zone UTC+0)
+   *  @return OFTrue if certificate expires before the given date,
+   *    or if the given date is invalid; OFFalse otherwise.
+   */
+  OFBool isCertExpiredAt(OFString& date);
+
+  /** returns true if the certificate is expired.
+   *  @return OFTrue if certificate is expired, OFFalse otherwise
+   */
+  OFBool isCertExpiredNow() const;
+
+  /** returns true if the certificate is not yet valid at the given date.
+   *  @param date a string in the format YYMMDDHHMMSSZ or YYYYMMDDHHMMSSZ
+   *    (where Z represents the letter 'Z', meaning time zone UTC+0)
+   *  @return OFTrue if certificate is not yet valid at the given date,
+   *    or if the given date is invalid; OFFalse otherwise.
+   */
+  OFBool isCertNotYetValidAt(OFString& date);
+
+  /** returns true if the certificate is not yet valid.
+   *  @return OFTrue if certificate is not yet valid, OFFalse otherwise
+   */
+  OFBool isCertNotYetValidNow() const;
+
+  /** this helper function converts a datetime in ASN1_GENERALIZEDTIME
+   *  format to OFDateTime.
+   *  @param d datetime in ASN1_GENERALIZEDTIME format
+   *  @param dt dt datetime stored in this parameter upon success
+   *  @return EC_Normal if successful, an error code otherwise
+   */
+  static OFCondition convertGeneralizedTime(const ASN1_GENERALIZEDTIME *d, OFDateTime& dt);
+
+  /** this helper function converts a datetime in ASN1_TIME format
+   *  (which is in fact an alias for ASN1_STRING) to OFDateTime.
+   *  @param d datetime in ASN1_TIME format
+   *  @param dt dt datetime stored in this parameter upon success
+   *  @return EC_Normal if successful, an error code otherwise
+   */
+  static OFCondition convertASN1Time(const ASN1_STRING *d, OFDateTime& dt);
+
 private:
 
   /// private undefined copy constructor
index 3473ae231405fbac6933f647cc5bb69836fccaf9..59ea7e319ae5a7a5b8c15b5a8cd1f295a576f8d6 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define SICERTVF_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/sitypes.h"
 
 #ifdef WITH_OPENSSL
 
+#include "dcmtk/dcmsign/sitypes.h"
+
 class SiCertificate;
 struct x509_store_st;
+struct x509_store_ctx_st;
+struct stack_st_X509; // this is STACK_OF(X509) in OpenSSL
 typedef struct x509_store_st X509_STORE;
+typedef struct x509_store_ctx_st X509_STORE_CTX;
 
 /** a class representing X.509 public key certificates.
  *  @remark this class is only available if DCMTK is compiled with
  *  OpenSSL support enabled.
  */
 class DCMTK_DCMSIGN_EXPORT SiCertificateVerifier
-{    
+{
 public:
 
   /// default constructor
   SiCertificateVerifier();
-  
+
   ///destructor
   virtual ~SiCertificateVerifier();
 
@@ -50,8 +54,18 @@ public:
    *  @param fileName path to the certificate file
    *  @param filetype file format: X509_FILETYPE_PEM or X509_FILETYPE_ASN1
    *  @return SI_EC_Normal if successful, an error code otherwise
-   */  
-  OFCondition addTrustedCertificateFile(const char *fileName, int fileType);
+   */
+  virtual OFCondition addTrustedCertificateFile(const char *fileName, int fileType);
+
+  /** loads an untrusted certificate from a file and adds it to the pool
+   *  of untrusted certificates. During certificate verification these will
+   *  only be accepted as intermediate CAs (not as root CA) and will undergo
+   *  additional scrutiny (e.g. check of the purpose extension, if present).
+   *  @param fileName path to the certificate file
+   *  @param filetype file format: X509_FILETYPE_PEM or X509_FILETYPE_ASN1
+   *  @return SI_EC_Normal if successful, an error code otherwise
+   */
+  virtual OFCondition addUntrustedCertificateFile(const char *fileName, int fileType);
 
   /** loads all files as certificates from the specified directory and adds them
    *  to the pool of trusted certificates.
@@ -59,15 +73,15 @@ public:
    *  @param filetype file format: X509_FILETYPE_PEM or X509_FILETYPE_ASN1
    *  @return SI_EC_Normal if successful, an error code otherwise
    */
-  OFCondition addTrustedCertificateDir(const char *pathName, int fileType);
+  virtual OFCondition addTrustedCertificateDir(const char *pathName, int fileType);
 
-  /** loads a certificate revocation list (CRL) in X.509 format from a file and 
+  /** loads a certificate revocation list (CRL) in X.509 format from a file and
    *  adds it to the pool of trusted certificates and CRLs.
    *  @param fileName path to the CRL file
    *  @param filetype file format: X509_FILETYPE_PEM or X509_FILETYPE_ASN1
    *  @return SI_EC_Normal if successful, an error code otherwise
-   */  
-  OFCondition addCertificateRevocationList(const char *fileName, int fileType);
+   */
+  virtual OFCondition addCertificateRevocationList(const char *fileName, int fileType);
 
   /** verifies a certificate against the known trusted CA certificates
    *  and certificate revocation lists. Returns a status flag and stores
@@ -76,14 +90,49 @@ public:
    *  @return SI_EC_Normal if successful, an error code otherwise.
    *     If the certificate could not be verified, returns SI_EC_VerificationFailed_NoTrust.
    */
-  OFCondition verifyCertificate(SiCertificate& certificate);
+  virtual OFCondition verifyCertificate(SiCertificate& certificate);
 
   /** returns an error string containing a textual description of the result
-   *  of the last call to verifyCertificate() if that call returned 
+   *  of the last call to verifyCertificate() if that call returned
    *  SI_EC_VerificationFailed_NoTrust.
    *  @return text string
    */
-  const char *lastError() const;
+  virtual const char *lastError() const;
+
+  /** returns true if the result of the last call to verifyCertificate()
+   *  was the status code indicating that the certificate has expired,
+   *  false otherwise
+   *  @return true if verifyCertificate() reported certificate expiry.
+   */
+  virtual OFBool lastErrorIsCertExpiry() const;
+
+  /** returns a pointer to the trusted certificate store managed by this object.
+   *  @return pointer to trusted certificate store
+   */
+  virtual X509_STORE *getTrustedCertStore();
+
+  /** returns a pointer to the stack of untrusted certificates managed by this object.
+   *  Note that the return type is equivalent to OpenSSL's STACK_OF(X509).
+   *  @return pointer to stack of untrusted certificates
+   */
+  virtual stack_st_X509 *getUntrustedCerts();
+
+  /** enable or disable the verification of certificate revocation lists.
+   *  When enabled, a CRL is expected to be present for every CA certificate,
+   *  and certificate verification will fail if no CRL is found.
+   *  @param enabled OFTrue to enable verification, OFFalse to disable
+   */
+  virtual void setCRLverification(OFBool enabled);
+
+  /** Callback function for certificate verification operations.
+   *  This method can be used by derived classes to examine and modify the
+   * result of a certificate verification.
+   *  @param deflt default return code that should be returned if the callback does
+   *    not modify the result of the verification
+   *  @param ctx certificate verification context object
+   *  @return result of the verification, 0 for error, 1 for no error, 2 for "policy checking complete".
+   */
+  virtual int verifyCallback(int deflt, X509_STORE_CTX *ctx);
 
 private:
 
@@ -94,7 +143,13 @@ private:
   SiCertificateVerifier& operator=(SiCertificateVerifier& arg);
 
   /// OpenSSL X.509 certificate store
-  X509_STORE* x509store;
+  X509_STORE *x509store;
+
+  /// OpenSSL X.509 stack of untrusted intermediate certificates
+  stack_st_X509 *x509untrusted;
+
+  /// flag indicating whether CRL verification should be enabled
+  OFBool enableCRLverification;
 
   /// OpenSSL X.509 certificate verification error code for the last operation
   long errorCode;
@@ -103,3 +158,4 @@ private:
 
 #endif
 #endif
+
index 189b55852d80f28d2f71a0ab31d8094107aa62e0..8ab1a5920300f50c9d42ddca8d1f8adcca50f0ab 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define SICREAPR_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/sibrsapr.h"   /* for SiBaseRSAProfile */
 
 #ifdef WITH_OPENSSL
 
+#include "dcmtk/dcmsign/sibrsapr.h"   /* for SiBaseRSAProfile */
+
 /** Creator RSA Digital Signature Profile
  *  @remark this class is only available if DCMTK is compiled with
  *  OpenSSL support enabled.
  */
 class DCMTK_DCMSIGN_EXPORT SiCreatorProfile: public SiBaseRSAProfile
-{ 
+{
 public:
 
   /// default constructor
-  SiCreatorProfile() { }
+  SiCreatorProfile();
 
   /// destructor
   virtual ~SiCreatorProfile() { }
-  
+
   /** checks whether an attribute with the given tag is required to be signed
-   *  for the current security profile.
+   *  for the current security profile if the attribute is present in the dataset
    *  @param key tag key to be checked
    *  @return true if required, false otherwise.
    */
-  virtual OFBool attributeRequired(const DcmTagKey& key) const;
+  virtual OFBool attributeRequiredIfPresent(const DcmTagKey& key) const;
+
+  /** checks whether all attributes that are required unconditionally
+   *  to be signed in this profile are included in the given tagList.
+   *  @param taglist attribute tag list
+   *  @return true if requirements for profile are fulfilled, false otherwise.
+   */
+  virtual OFBool checkRequiredAttributeList(DcmAttributeTag& tagList) const;
+
+  /** some digital signature profiles specify conditions under which certain
+   *  attributes must be included into the signature.
+   *  This method allows the signature profile to inspect the dataset in order
+   *  to determine whether or not the conditions are met.
+   *  This method should be called before DcmSignature::createSignature() is executed.
+   *  @param item the dataset or item to which the signature will be added
+   *  @return status code
+   */
+  virtual OFCondition inspectSignatureDataset(DcmItem &item);
+
+  /** returns true if this signature profile only applies to main dataset level
+   *  @return OFTrue if this signature profile only applies to main dataset level, OFFalse otherwise
+   */
+  virtual OFBool mainDatasetRequired() const;
+
+private:
 
+  /// flag indicating whether or not the signature dataset contains the raw data module
+  OFBool containsRawData_;
 };
 
 #endif
index 02759347dbdc139544e0386ec9c9844e27e58d3e..4dc5ac14b8526f2f58b5b9b4a0ee6a87cb7b0d21 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define SIDSA_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/sialgo.h"
 
 #ifdef WITH_OPENSSL
 
+#include "dcmtk/dcmsign/sialgo.h"
 #include "dcmtk/ofstd/oftypes.h"
 
 class SiPrivateKey;
diff --git a/dcmsign/include/dcmtk/dcmsign/siecdsa.h b/dcmsign/include/dcmtk/dcmsign/siecdsa.h
new file mode 100644 (file)
index 0000000..4883cd6
--- /dev/null
@@ -0,0 +1,115 @@
+/*
+ *
+ *  Copyright (C) 1998-2019, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmsign
+ *
+ *  Author: Marco Eichelberg
+ *
+ *  Purpose:
+ *    classes: SiDSA
+ *
+ */
+
+#ifndef SIECDSA_H
+#define SIECDSA_H
+
+#include "dcmtk/config/osconfig.h"
+
+#ifdef WITH_OPENSSL
+
+#include "dcmtk/dcmsign/sialgo.h"
+#include "dcmtk/ofstd/oftypes.h"
+
+class SiPrivateKey;
+struct ec_key_st;
+typedef struct ec_key_st EC_KEY;
+
+/**
+ *  This class implements the ECDSA public key crypto algorithms.
+ *  @remark This class is only available if DCMTK is compiled with
+ *  OpenSSL support enabled.
+ */
+
+class DCMTK_DCMSIGN_EXPORT SiECDSA : public SiAlgorithm
+{
+public:
+
+  /** constructor
+   *  @param pointer to public ECDSA key
+   */
+  SiECDSA(EC_KEY *key);
+
+  /// destructor
+  virtual ~SiECDSA();
+
+  /** creates a signature.
+   *  @param inputHash array of hash key bytes that are to be signed
+   *  @param inputHashSize length of hash key array in bytes
+   *  @param inputHashAlgorithm MAC algorithm used for creation of hash key. Ignored for ECDSA signatures.
+   *  @param outputSignature pointer to array of at least getSize() which must be allocated by caller.
+   *  @param outputSignatureSize returns the number of bytes written to outputSignature.
+   *  @return SI_EC_Normal if successful, errorcode otherwise.
+   */
+  virtual OFCondition sign(
+    const unsigned char *inputHash,
+    unsigned long inputHashSize,
+    E_MACType inputHashAlgorithm,
+    unsigned char *outputSignature,
+    unsigned long &outputSignatureSize);
+
+  /** verifies a signature.
+   *  @param inputHash array of bytes containing hash key to be verified against signature
+   *  @param inputHashSize length of hash key array in bytes
+   *  @param inputHashAlgorithm MAC algorithm used for creation of hash key. Ignored for ECDSA signatures.
+   *  @param inputSignature array of bytes containing signature to be verified
+   *  @param inputSignatureSize length of signature array in bytes
+   *  @param verified returns whether the signature was successfully verified
+   *  @return SI_EC_Normal if successful, errorcode otherwise.
+   */
+  virtual OFCondition verify(
+    const unsigned char *inputHash,
+    unsigned long inputHashSize,
+    E_MACType inputHashAlgorithm,
+    const unsigned char *inputSignature,
+    unsigned long inputSignatureSize,
+    OFBool &verified);
+
+  /** returns the size of a block of encrypted/decrypted ciphertext in bytes.
+   *  The result depends on the public key algorithm, key size and padding scheme.
+   *  In general the input to decrypt() or encrypt() must be less than or equal
+   *  to this block size.  The output of decrypt() or encrypt() is always equal
+   *  to this block size.
+   *  @return block size for this public key cryptosystem and key
+   */
+  virtual unsigned long getSize() const;
+
+  /** returns the type of public key algorithm computed by this object
+   *  @return type of public key algorithm
+   */
+  virtual E_KeyType keyType() const;
+
+private:
+
+  /// private undefined copy constructor
+  SiECDSA(SiECDSA& arg);
+
+  /// private undefined copy assignment operator
+  SiECDSA& operator=(SiECDSA& arg);
+
+  /// ECDSA key used for signature/verification
+  EC_KEY *ecdsa;
+
+};
+
+#endif
+#endif
diff --git a/dcmsign/include/dcmtk/dcmsign/siexit.h b/dcmsign/include/dcmtk/dcmsign/siexit.h
new file mode 100644 (file)
index 0000000..03f6c66
--- /dev/null
@@ -0,0 +1,56 @@
+/*
+ *
+ *  Copyright (C) 1998-2020, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmsign
+ *
+ *  Author: Marco Eichelberg
+ *
+ *  Purpose: exit codes for dcmsign
+ *
+ */
+
+#ifndef SIEXIT_H
+#define SIEXIT_H
+
+#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
+
+#ifdef WITH_OPENSSL
+
+// exit code constants in addition to those defined in "dcmtk/ofstd/ofexit.h"
+
+// input file errors (20-39)
+#define EXITCODE_CANNOT_READ_TAG_FILE            30
+#define EXITCODE_CANNOT_READ_TSQ_FILE            31
+#define EXITCODE_CANNOT_READ_TSR_FILE            32
+#define EXITCODE_CANNOT_READ_UID_FILE            33
+
+// output file errors (40-59)
+#define EXITCODE_CANNOT_WRITE_SUPPORT_FILE       46
+
+// processing errors (80-99)
+#define EXITCODE_CANNOT_ACCESS_SIGNATURE         80
+#define EXITCODE_CANNOT_ACCESS_TS                81
+#define EXITCODE_CANNOT_INSERT_TS                82
+#define EXITCODE_SIGNATURE_REMOVAL_FAILED        83
+#define EXITCODE_SIGNATURE_UID_NOT_FOUND         84
+#define EXITCODE_SIGNATURE_CREATION_FAILED       85
+#define EXITCODE_SYNTAX_ERROR_IN_TAG_FILE        86
+#define EXITCODE_TS_CONSISTENCY_CHECK_FAILED     87
+
+// application specific errors (100-119)
+#define EXITCODE_NO_SIGNATURES_PRESENT           100
+#define EXITCODE_SIGNATURE_VERIFICATION_FAILED   101
+#define EXITCODE_SIGNATURE_VERIFICATION_POLICY   102
+
+#endif
+#endif
index 4101404cf548072cae2826551b2ba8ad931744ca..86faf2cc42700a3cec8fee45fa09f548bc5b3aab 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define SIMAC_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/sitypes.h"
 
 #ifdef WITH_OPENSSL
 
+#include "dcmtk/dcmsign/sitypes.h"
+
 /**
  * a base class for all classes that implement hash functions.
  * @remark this class is only available if DCMTK is compiled with
index 035e3e51b67bd6b6ccad9d83b9c88d6867a2570e..fe0eda80e9a9514a796ee03e03921b1a67836e56 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define SIMACCON_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/sitypes.h"
 
 #ifdef WITH_OPENSSL
 
+#include "dcmtk/dcmsign/sitypes.h"
 #include "dcmtk/dcmdata/dcostrmb.h"  /* for DcmOutputBufferStream */
 #include "dcmtk/dcmdata/dcxfer.h"    /* for E_TransferSyntax */
 #include "dcmtk/dcmdata/dcdeftag.h"
@@ -50,14 +50,14 @@ public:
 
   /// constructor
   SiMACConstructor();
-  
+
   /// destructor
   virtual ~SiMACConstructor();
 
   /** encodes a DICOM dataset (or parts of it) as a byte stream in the format
    *  required for DICOM digital signatures and feeds the byte stream into
    *  the given MAC codec.
-   *  If a dump file was set with setDumpFile(), the byte stream is written 
+   *  If a dump file was set with setDumpFile(), the byte stream is written
    *  to file as well.
    *  @param item the DICOM dataset to be encoded
    *  @param mac the MAC codec into which the resulting byte stream is fed
@@ -69,28 +69,47 @@ public:
    *     attribute tag is contained in this list; the items and elements within the items
    *     are not encoded.
    *  @param tagListIn optional parameter restricting the parts of the dataset
-   *     to be encoded. Only elements which are present in this list of tags, 
+   *     to be encoded. Only elements which are present in this list of tags,
    *     which are signable (see DcmTagKey::isSignable()) and are present in the dataset
    *     are encoded.  Upon verification of a signature the caller might wish to compare
-   *     tagListIn and tagListOut after successful return to see whether the lists of 
+   *     tagListIn and tagListOut after successful return to see whether the lists of
    *     attributes are the same.
    *     If parameter is absent or NULL, a global match is assumed, i.e. all elements
    *     of the dataset which are present and signable are encoded.
    *  @return status code
    */
   OFCondition encodeDataset(
-    DcmItem& item, 
-    SiMAC& mac, 
+    DcmItem& item,
+    SiMAC& mac,
     E_TransferSyntax oxfer,
     DcmAttributeTag &tagListOut,
     DcmAttributeTag *tagListIn = NULL);
 
+   /** encodes a DICOM dataset (or parts of it) as a byte stream in the format
+   *  required for DICOM digital signatures and feeds the byte stream into
+   *  the given MAC codec, for the purpose of signature verification
+   *  If a dump file was set with setDumpFile(), the byte stream is written
+   *  to file as well.
+   *  @param item the DICOM dataset to be encoded
+   *  @param mac the MAC codec into which the resulting byte stream is fed
+   *  @param oxfer the transfer syntax to be used when encoding the dataset.
+   *     The caller might wish to use DcmItem::canWriteXfer() to check beforehand
+   *     whether this transfer syntax can be used.
+   *  @param tagListIn list of elements to be encoded.
+   *  @return status code
+   */
+   OFCondition encodeDatasetForVerification(
+    DcmItem& item,
+    SiMAC& mac,
+    E_TransferSyntax oxfer,
+    DcmAttributeTag *tagListIn);
+
   /** encodes the contents of the digital signature sequence
    *  except CertificateOfSigner, Signature, CertifiedTimestampType
    *  and CertifiedTimestamp as a byte stream in the format
    *  required for DICOM digital signatures and feeds the byte stream into
    *  the given MAC codec.
-   *  If a dump file was set with setDumpFile(), the byte stream is written 
+   *  If a dump file was set with setDumpFile(), the byte stream is written
    *  to file as well.
    *  @param signatureItem the DICOM digital signature item to be encoded
    *  @param mac the MAC codec into which the resulting byte stream is fed
@@ -100,8 +119,8 @@ public:
    *  @return status code
    */
   OFCondition encodeDigitalSignatureItem(
-    DcmItem& signatureItem, 
-    SiMAC& mac, 
+    DcmItem& signatureItem,
+    SiMAC& mac,
     E_TransferSyntax oxfer);
 
   /** flushes all buffers inside this object, finalizing the MAC code
@@ -130,8 +149,8 @@ private:
    */
   OFCondition flushBuffer(SiMAC& mac);
 
-  /** feeds a DcmElement into the MAC data stream if is signable. 
-   *  If the element is a sequence, all signable elements from all items are added. 
+  /** feeds a DcmElement into the MAC data stream if is signable.
+   *  If the element is a sequence, all signable elements from all items are added.
    *  @param element pointer to element, must not be NULL
    *  @param mac MAC to use
    *  @param oxfer transfer syntax in which data is encoded
@@ -154,7 +173,7 @@ private:
 
   /// the internal buffer stream
   DcmOutputBufferStream stream;
-  
+
   /** if nonzero, the data fed to the MAC algorithm
    *  is also stored in this file.
    */
index 06048e5d2fd1c31b17869ffc9559dafb34ccd7f7..1ccaa437fdb5b6bfa3b6c07e553b8040c7adeafa 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define SIMD5_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/simac.h"
-#include "dcmtk/dcmsign/sitypes.h"
 
 #ifdef WITH_OPENSSL
 
+#include "dcmtk/dcmsign/simac.h"
+#include "dcmtk/dcmsign/sitypes.h"
+
 struct MD5state_st;
 typedef struct MD5state_st MD5_CTX;
 
index 6a7114909e7e0e92cad8c9169b922a2be87ca722..c09d5053901781fab8bd82c06a77fb15bb1f865c 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define SINULLPR_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/sisprof.h"   /* for SiSecurityProfile */
 
 #ifdef WITH_OPENSSL
 
-/** defines a "null" security profile that does not require or forbid any 
+#include "dcmtk/dcmsign/sisprof.h"   /* for SiSecurityProfile */
+
+/** defines a "null" security profile that does not require or forbid any
  *  MAC algorithm, signature algorithm, or attribute tag. This class can be
  *  used to clean up a proposed attribute list against a dataset.
  *  @remark this class is only available if DCMTK is compiled with
@@ -43,7 +44,7 @@ public:
 
   /// destructor
   virtual ~SiNullProfile() { }
-  
+
   /** checks whether the given MAC type can be used with this security profile.
    *  @param macType MAC type to be checked
    *  @return true if MAC type is allowable for this profile, false otherwise.
@@ -63,11 +64,18 @@ public:
   virtual OFBool isAllowableTransferSyntax(E_TransferSyntax xfer) const;
 
   /** checks whether an attribute with the given tag is required to be signed
-   *  for the current security profile.
+   *  for the current security profile if the attribute is present in the dataset
    *  @param key tag key to be checked
    *  @return true if required, false otherwise.
    */
-  virtual OFBool attributeRequired(const DcmTagKey& key) const;
+  virtual OFBool attributeRequiredIfPresent(const DcmTagKey& key) const;
+
+  /** checks whether all attributes that are required unconditionally
+   *  to be signed in this profile are included in the given tagList.
+   *  @param taglist attribute tag list
+   *  @return true if requirements for profile are fulfilled, false otherwise.
+   */
+  virtual OFBool checkRequiredAttributeList(DcmAttributeTag& tagList) const;
 
   /** checks whether an attribute with the given tag must not be signed
    *  for the current security profile.
@@ -76,6 +84,21 @@ public:
    */
   virtual OFBool attributeForbidden(const DcmTagKey& key) const;
 
+  /** some digital signature profiles specify conditions under which certain
+   *  attributes must be included into the signature.
+   *  This method allows the signature profile to inspect the dataset in order
+   *  to determine whether or not the conditions are met.
+   *  This method should be called before DcmSignature::createSignature() is executed.
+   *  @param item the dataset or item to which the signature will be added
+   *  @return status code
+   */
+  virtual OFCondition inspectSignatureDataset(DcmItem &item);
+
+  /** returns true if this signature profile only applies to main dataset level
+   *  @return OFTrue if this signature profile only applies to main dataset level, OFFalse otherwise
+   */
+  virtual OFBool mainDatasetRequired() const;
+
 };
 
 #endif
index ad96a449d02c40fe7d17063c1a0f164762f00624..90458af68866492b159ede77d202bd869d298420 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define SIPRIVAT_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/sitypes.h"
 
 #ifdef WITH_OPENSSL
 
+#include "dcmtk/dcmsign/sitypes.h"
 #include "dcmtk/ofstd/ofstring.h"
 
 class SiAlgorithm;
diff --git a/dcmsign/include/dcmtk/dcmsign/sipurpos.h b/dcmsign/include/dcmtk/dcmsign/sipurpos.h
new file mode 100644 (file)
index 0000000..8c4e963
--- /dev/null
@@ -0,0 +1,156 @@
+/*
+ *
+ *  Copyright (C) 2019, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmsign
+ *
+ *  Author: Marco Eichelberg
+ *
+ *  Purpose:
+ *    classes: SiSignaturePurpose
+ *
+ */
+
+#ifndef SIPURPOS_H
+#define SIPURPOS_H
+
+#include "dcmtk/config/osconfig.h"
+
+#ifdef WITH_OPENSSL
+
+#include "dcmtk/dcmsign/sidefine.h"
+#include "dcmtk/ofstd/ofstream.h"
+
+class DcmItem;
+class OFCondition;
+
+/** Helper class for the Digital Signature Purpose Code Sequence.
+ *  @remark this class is only available if DCMTK is compiled with
+ *  OpenSSL support enabled.
+ */
+class DCMTK_DCMSIGN_EXPORT SiSignaturePurpose
+{
+public:
+
+    /** purpose of digital signature as defined in DICOM BCID 7007.
+     *  @remark this enum is only available if DCMTK is compiled with
+     *  OpenSSL support enabled.
+     */
+    enum E_SignaturePurposeType
+    {
+      /// no signature purpose specified
+      ESP_none = 0,
+
+      /// Author's Signature
+      ESP_AuthorsSignature = 1,
+
+      /// Coauthor's Signature
+      ESP_CoauthorsSignature = 2,
+
+      /// Co-participant's Signature
+      ESP_CoparticipantsSignature = 3,
+
+      /// Transcriptionist/Recorder Signature
+      ESP_TranscriptionistSignature = 4,
+
+      /// Verification Signature
+      ESP_VerificationSignature = 5,
+
+      /// Validation Signature
+      ESP_ValidationSignature = 6,
+
+      /// Consent Signature
+      ESP_ConsentSignature = 7,
+
+      /// Signature Witness Signature
+      ESP_SignatureWitnessSignature = 8,
+
+      /// Event Witness Signature
+      ESP_EventWitnessSignature = 9,
+
+      /// Identity Witness Signature
+      ESP_IdentityWitnessSignature = 10,
+
+      /// Consent Witness Signature
+      ESP_ConsentWitnessSignature = 11,
+
+      /// Interpreter Signature
+      ESP_InterpreterSignature = 12,
+
+      /// Review Signature
+      ESP_ReviewSignature = 13,
+
+      /// Source Signature
+      ESP_SourceSignature = 14,
+
+      /// Addendum Signature
+      ESP_AddendumSignature = 15,
+
+      /// Modification Signature
+      ESP_ModificationSignature = 16,
+
+      /// Administrative (Error/Edit) Signature
+      ESP_AdministrativeSignature = 17,
+
+      /// Timestamp Signature
+      ESP_TimestampSignature = 18
+
+    };
+
+    /** return the code value for the given signature purpose
+     *  @return code value for the given signature purpose, NULL for ESP_none
+     */
+    static const char *getCodeValue(E_SignaturePurposeType purpose);
+
+    /** return the code meaning for the given signature purpose
+     *  @return code meaning for the given signature purpose, NULL for ESP_none
+     */
+    static const char *getCodeMeaning(E_SignaturePurposeType purpose);
+
+    /** return the coding scheme designator for the given signature purpose
+     *  @return coding scheme designator for the given signature purpose
+     */
+    static const char *getCodingSchemeDesignator(E_SignaturePurposeType purpose);
+
+    /** insert a digital signature purpose code sequence into the given DICOM item
+     *  @param seqItem item into which the sequence is inserted. This should be an item
+     *    of the DigitalSignaturesSequence.
+     *  @param sigPurpose signature purpose. If the purpose is ESP_none, nothing will be 
+     *    inserted and this method will immediately return with EC_Normal
+     *  @return EC_Normal if successful, an error code otherwise
+     */
+    static OFCondition insertDigitalSignaturePurposeCodeSQ(DcmItem& seqItem, E_SignaturePurposeType sigPurpose);
+
+    /** determine the signature purpose to be used, and prints a warning to the logger if
+     *  an override required by the signature profile causes the user selection to be ignored.
+     *  @param currentPurpose signature purpose selected by the user
+     *  @param overridePurpose override signature purpose required by the signature profile
+     *  @return signature purpose to be used for the digital signature purpose code sequence
+     */
+    static E_SignaturePurposeType determineOverridePurpose(E_SignaturePurposeType currentPurpose, E_SignaturePurposeType overridePurpose);
+
+    /** look-up signature purpose enum by number
+     *  @param num number, 0 for ESP_none, 1 for ESP_AuthorsSignature etc.
+     *  @return signature purpose enum or ESP_none if number too high.
+     */
+    static E_SignaturePurposeType lookup(size_t num);
+
+    /** print a list of all signature purpose codes supported by this helper class.
+     *  This is used by dcmsign --list-purposes.
+     *  @param out output stream to print to
+     */
+    static void printSignatureCodes(STD_NAMESPACE ostream& out);
+
+};
+
+#endif
+#endif
index 2cfadba46368a23d2fd61a7888c9c9d4bbd9a20c..3381bda90ba036553c893dc94e9672df4f8aa408 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define SIRIPEMD_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/simac.h"
-#include "dcmtk/dcmsign/sitypes.h"
 
 #ifdef WITH_OPENSSL
 
+#include "dcmtk/dcmsign/simac.h"
+#include "dcmtk/dcmsign/sitypes.h"
+
 struct RIPEMD160state_st;
 typedef struct RIPEMD160state_st RIPEMD160_CTX;
 
index d71a5c096baca5b6137d8ddc7779ae3cd73f79d1..7e08958953a95fc3a782fead88b06bd9fb03ee9e 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define SIRSA_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/sialgo.h"
 
 #ifdef WITH_OPENSSL
 
+#include "dcmtk/dcmsign/sialgo.h"
 #include "dcmtk/ofstd/oftypes.h"
 
 class SiPrivateKey;
index 98b78a3d8e652aefc7659ffcab586aa82db47552..db58e2f219073b5af135fc8ffa5f8e9f375bccab 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define SISHA1_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/simac.h"
-#include "dcmtk/dcmsign/sitypes.h"
 
 #ifdef WITH_OPENSSL
 
+#include "dcmtk/dcmsign/simac.h"
+#include "dcmtk/dcmsign/sitypes.h"
+
 struct SHAstate_st;
 typedef struct SHAstate_st SHA_CTX;
 
index e81aad050dc88ce3fcd1e7207ff592d38ad0b31a..69d1e54d0c32d6bb53ed93930a412673008bf967 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define SISPROF_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/sitypes.h"  /* for E_KeyType */
 
 #ifdef WITH_OPENSSL
 
-#include "dcmtk/dcmdata/dcxfer.h"   /* for E_TransferSyntax */
+#include "dcmtk/dcmsign/sitypes.h"   /* for E_KeyType */
+#include "dcmtk/dcmsign/sipurpos.h"  /* for E_SignaturePurposeType */
+#include "dcmtk/dcmdata/dcxfer.h"    /* for E_TransferSyntax */
 
 class SiAlgorithm;
 class DcmItem;
@@ -49,7 +50,7 @@ public:
 
   /// destructor
   virtual ~SiSecurityProfile() { }
-  
+
   /** checks whether the given MAC type can be used with this security profile.
    *  @param macType MAC type to be checked
    *  @return true if MAC type is allowable for this profile, false otherwise.
@@ -67,7 +68,7 @@ public:
    *  @return true if public key algorithm is allowable for this profile, false otherwise.
    */
   virtual OFBool isAllowableAlgorithmType(E_KeyType keyType) const = 0;
-  
+
   /** checks whether the given public/private key object can be used with this security profile.
    *  @param algo object to be checked
    *  @return true if object is allowable for this profile, false otherwise.
@@ -79,13 +80,13 @@ public:
    *  @return true if transfer syntax is allowable for this profile, false otherwise.
    */
   virtual OFBool isAllowableTransferSyntax(E_TransferSyntax xfer) const = 0;
-  
+
   /** checks whether an attribute with the given tag is required to be signed
-   *  for the current security profile.
+   *  for the current security profile if the attribute is present in the dataset
    *  @param key tag key to be checked
    *  @return true if required, false otherwise.
    */
-  virtual OFBool attributeRequired(const DcmTagKey& key) const = 0;
+  virtual OFBool attributeRequiredIfPresent(const DcmTagKey& key) const = 0;
 
   /** checks whether an attribute with the given tag must not be signed
    *  for the current security profile.
@@ -93,7 +94,7 @@ public:
    *  @return true if attribute must not be signed, false otherwise.
    */
   virtual OFBool attributeForbidden(const DcmTagKey& key) const = 0;
-  
+
   /** updates the given list of attribute tags according to the
    *  requirements of the current security profile. For all elements present in the
    *  dataset, the attribute tag is inserted or removed from the list if required by the profile.
@@ -103,14 +104,50 @@ public:
    */
   virtual OFCondition updateAttributeList(DcmItem &item, DcmAttributeTag& tagList);
 
+  /** create a maximum list of attribute tags according to the
+   *  requirements of the current security profile. For all elements present in the
+   *  dataset, the attribute tag is inserted if permitted by the profile.
+   *  @param item dataset to be handled
+   *  @param tagList attribute tag list to be created
+   *  @return status code
+   */
+  virtual OFCondition createAttributeList(DcmItem &item, DcmAttributeTag& tagList);
+
   /** checks whether the given list of attribute tags fulfils the requirements
-   *  of the current security profile for the given dataset. 
+   *  of the current security profile for the given dataset.
    *  @param item dataset to be checked
-   *  @param tagList attribute tag list. 
+   *  @param tagList attribute tag list.
    *  @return true if minimum requirements for profile are fulfilled, false otherwise.
-   */ 
+   */
   virtual OFBool checkAttributeList(DcmItem &item, DcmAttributeTag& tagList);
 
+  /** checks whether all attributes that are required unconditionally
+   *  to be signed in this profile are included in the given tagList.
+   *  @param taglist attribute tag list
+   *  @return true if requirements for profile are fulfilled, false otherwise.
+   */
+  virtual OFBool checkRequiredAttributeList(DcmAttributeTag& tagList) const = 0;
+
+  /** some digital signature profiles specify conditions under which certain
+   *  attributes must be included into the signature.
+   *  This method allows the signature profile to inspect the dataset in order
+   *  to determine whether or not the conditions are met.
+   *  This method should be called before DcmSignature::createSignature() is executed.
+   *  @param item the dataset or item to which the signature will be added
+   *  @return status code
+   */
+  virtual OFCondition inspectSignatureDataset(DcmItem &item) = 0;
+
+  /** return the required digital signature purpose for this signature profile
+   *  @return required signature purpose if any, ESP_none otherwise
+   */
+  virtual SiSignaturePurpose::E_SignaturePurposeType getOverrideSignaturePurpose() const;
+
+  /** returns true if this signature profile only applies to main dataset level
+   *  @return OFTrue if this signature profile only applies to main dataset level, OFFalse otherwise
+   */
+  virtual OFBool mainDatasetRequired() const = 0;
+
   /** checks if the given tag key is contained in the given list.
    *  @param tagList list of tag keys
    *  @param key tag key
diff --git a/dcmsign/include/dcmtk/dcmsign/sisrpr.h b/dcmsign/include/dcmtk/dcmsign/sisrpr.h
new file mode 100644 (file)
index 0000000..bd67053
--- /dev/null
@@ -0,0 +1,77 @@
+/*
+ *
+ *  Copyright (C) 2019, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmsign
+ *
+ *  Author: Marco Eichelberg
+ *
+ *  Purpose:
+ *    classes: SiStructuredReportingProfile
+ *
+ */
+
+#ifndef SISRPR_H
+#define SISRPR_H
+
+#include "dcmtk/config/osconfig.h"
+#include "dcmtk/dcmsign/sibrsapr.h"   /* for SiBaseRSAProfile */
+
+#ifdef WITH_OPENSSL
+
+/** Structured Reporting RSA Digital Signature Profile
+ *  @remark this class is only available if DCMTK is compiled with
+ *  OpenSSL support enabled.
+ */
+class DCMTK_DCMSIGN_EXPORT SiStructuredReportingProfile: public SiBaseRSAProfile
+{
+public:
+
+  /// default constructor
+  SiStructuredReportingProfile() { }
+
+  /// destructor
+  virtual ~SiStructuredReportingProfile() { }
+
+  /** checks whether an attribute with the given tag is required to be signed
+   *  for the current security profile if the attribute is present in the dataset
+   *  @param key tag key to be checked
+   *  @return true if required, false otherwise.
+   */
+  virtual OFBool attributeRequiredIfPresent(const DcmTagKey& key) const;
+
+  /** checks whether all attributes that are required unconditionally
+   *  to be signed in this profile are included in the given tagList.
+   *  @param taglist attribute tag list
+   *  @return true if requirements for profile are fulfilled, false otherwise.
+   */
+  virtual OFBool checkRequiredAttributeList(DcmAttributeTag& tagList) const;
+
+  /** some digital signature profiles specify conditions under which certain
+   *  attributes must be included into the signature.
+   *  This method allows the signature profile to inspect the dataset in order
+   *  to determine whether or not the conditions are met.
+   *  This method should be called before DcmSignature::createSignature() is executed.
+   *  @param item the dataset or item to which the signature will be added
+   *  @return status code
+   */
+  virtual OFCondition inspectSignatureDataset(DcmItem &item);
+
+  /** returns true if this signature profile only applies to main dataset level
+   *  @return OFTrue if this signature profile only applies to main dataset level, OFFalse otherwise
+   */
+  virtual OFBool mainDatasetRequired() const;
+
+};
+
+#endif
+#endif
diff --git a/dcmsign/include/dcmtk/dcmsign/sisrvpr.h b/dcmsign/include/dcmtk/dcmsign/sisrvpr.h
new file mode 100644 (file)
index 0000000..af6fc57
--- /dev/null
@@ -0,0 +1,78 @@
+/*
+ *
+ *  Copyright (C) 2019, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmsign
+ *
+ *  Author: Marco Eichelberg
+ *
+ *  Purpose:
+ *    classes: SiStructuredReportingVerificationProfile
+ *
+ */
+
+#ifndef SISRVPR_H
+#define SISRVPR_H
+
+#include "dcmtk/config/osconfig.h"
+
+#ifdef WITH_OPENSSL
+
+#include "dcmtk/dcmsign/sisrpr.h"   /* for SiStructuredReportingProfile */
+
+/** Structured Reporting RSA Digital Signature Profile - Verification Signature
+ *  @remark this class is only available if DCMTK is compiled with
+ *  OpenSSL support enabled.
+ */
+class DCMTK_DCMSIGN_EXPORT SiStructuredReportingVerificationProfile: public SiStructuredReportingProfile
+{
+public:
+
+  /// default constructor
+  SiStructuredReportingVerificationProfile() { }
+
+  /// destructor
+  virtual ~SiStructuredReportingVerificationProfile() { }
+
+  /** checks whether an attribute with the given tag is required to be signed
+   *  for the current security profile if the attribute is present in the dataset
+   *  @param key tag key to be checked
+   *  @return true if required, false otherwise.
+   */
+  virtual OFBool attributeRequiredIfPresent(const DcmTagKey& key) const;
+
+  /** checks whether all attributes that are required unconditionally
+   *  to be signed in this profile are included in the given tagList.
+   *  @param taglist attribute tag list
+   *  @return true if requirements for profile are fulfilled, false otherwise.
+   */
+  virtual OFBool checkRequiredAttributeList(DcmAttributeTag& tagList) const;
+
+  /** some digital signature profiles specify conditions under which certain
+   *  attributes must be included into the signature.
+   *  This method allows the signature profile to inspect the dataset in order
+   *  to determine whether or not the conditions are met.
+   *  This method should be called before DcmSignature::createSignature() is executed.
+   *  @param item the dataset or item to which the signature will be added
+   *  @return status code
+   */
+  virtual OFCondition inspectSignatureDataset(DcmItem &item);
+
+  /** return the required digital signature purpose for this signature profile
+   *  @return for this class, this method always returns ESP_VerificationSignature.
+   */
+  virtual SiSignaturePurpose::E_SignaturePurposeType getOverrideSignaturePurpose() const;
+
+};
+
+#endif
+#endif
diff --git a/dcmsign/include/dcmtk/dcmsign/sitsfs.h b/dcmsign/include/dcmtk/dcmsign/sitsfs.h
new file mode 100644 (file)
index 0000000..91bb67c
--- /dev/null
@@ -0,0 +1,131 @@
+/*
+ *
+ *  Copyright (C) 1998-2019, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmsign
+ *
+ *  Author: Marco Eichelberg
+ *
+ *  Purpose:
+ *    classes: SiTimeStampFS
+ *
+ */
+
+#ifndef SITSFS_H
+#define SITSFS_H
+
+#include "dcmtk/config/osconfig.h"
+
+#ifdef WITH_OPENSSL
+
+#include "dcmtk/dcmsign/sitstamp.h" /* for class SiTimeStamp */
+#include "dcmtk/ofstd/ofstring.h"   /* for class OFString */
+
+/** timestamp client based on filesystem interactions.
+ *  This timestamp client will write a timestamp query in DES encoding to file.
+ *  The interaction with the time stamp authority must then take place separately
+ *  (e.g. manually, using a command line tool like curl). This client then offers
+ *  functionality to import a timestamp reponse (i.e. a timestamp) from file
+ *  and place it into the signed DICOM file for which the timestamp was requested.
+ *  @remark this class is only available if DCMTK is compiled with OpenSSL support enabled.
+ */
+class DCMTK_DCMSIGN_EXPORT SiTimeStampFS : public SiTimeStamp
+{
+public:
+
+  /// default constructor
+  SiTimeStampFS();
+
+  /// destructor
+  virtual ~SiTimeStampFS();
+
+  /** takes a block of raw data, creates a time stamp query for a hash of this
+   *  raw data, and stores it locally in this object.
+   *  @param inputData pointer to raw data
+   *  @param inputDataSize length of raw data block in bytes
+   *  @return status code
+   */
+  virtual OFCondition stamp(
+    const unsigned char *inputData,
+    unsigned long inputDataSize);
+
+  /** writes the time stamp query created with SiTimeStampFS::stamp() to a file.
+   *  Also writes a "UID file" that contains the Digital Signature UID of the signature
+   *  to which the timestamp request belongs. This file will be read later by the
+   *  import function. The filenames of timestamp query file and UID file must be
+   *  set prior to calling this method.
+   *  @param item item of the DigitalSignatureSQ to which the timestamp is written
+   *  @return dcmdata OFCondition status code
+   */
+  virtual OFCondition write(DcmItem& item);
+
+  /** set the time stamp query filename to be written
+   *  @param fname filename
+   */
+  virtual void setTSQFilename(const char *fname);
+
+  /** set the time stamp response filename to be read
+   *  @param fname filename
+   */
+  virtual void setTSRFilename(const char *fname);
+
+  /** set the uid file filename to be written
+   *  @param fname filename
+   */
+  virtual void setUIDFilename(const char *fname);
+
+  /** load UID file and retrieve digital signature UID
+   *  @param uid digital signature returned in this parameter if successful
+   * @return EC_Normal if successful, an error code otherwise.
+   */
+  virtual OFCondition getUIDFromFile(OFString& uid);
+
+  /** load timestamp query from file
+   *  @return status code
+   */
+  virtual OFCondition load_ts_query_from_file();
+
+  /** load timestamp response from file
+   *  @return status code
+   */
+  virtual OFCondition load_ts_response_from_file();
+
+  /** check consistency between timestamp query (if available), timestamp
+   *  response and DICOM digital signature. Query and response files must have
+   *  been loaded prior to this method call.
+   *  @param ditem item of the DigitalSignaturesSequence to which this timestamp belongs
+   *  @return status code
+   */
+  virtual OFCondition check_ts_response(DcmItem& ditem);
+
+  /** insert timestamp token into DICOM dataset
+   *  The response file must have been loaded and checked prior to this method call.
+   *  @param ditem item of the DigitalSignaturesSequence to which this timestamp is written
+   *  @return status code
+   */
+  virtual OFCondition write_ts_token(DcmItem& ditem);
+
+private:
+
+  /// filename of the timestamp query file to be written
+  OFString tsqFilename_;
+
+  /// filename of the timestamp response file to be read
+  OFString tsrFilename_;
+
+  /// filename of the UID file to be written
+  OFString uidFilename_;
+
+};
+
+#endif
+#endif
index de144dd4e059eea8a6da030b0bce38e018741062..9e329dc5c6325f5e6c03c2077f78d9e97aa75750 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #define SITSTAMP_H
 
 #include "dcmtk/config/osconfig.h"
-#include "dcmtk/dcmsign/sitypes.h"
 
 #ifdef WITH_OPENSSL
 
+#include "dcmtk/dcmsign/sitypes.h"
+#include "dcmtk/ofstd/ofstring.h"
+
+// forward declarations
 class DcmItem;
-/** pure virtual base class for a timestamp client.
+class SiCertificateVerifier;
+class SiCertificate;
+struct TS_req_st;
+struct TS_resp_st;
+struct TS_tst_info_st;
+typedef struct TS_req_st TS_REQ;
+typedef struct TS_resp_st TS_RESP;
+typedef struct TS_tst_info_st TS_TST_INFO;
+typedef struct pkcs7_st PKCS7;
+
+/** Base class for a timestamp client.
  *  Instances of derived classes are able to request timestamps from a timestamp service.
- *  Timestamps are not supported (yet).
- *  @remark this class is only available if DCMTK is compiled with
- *  OpenSSL support enabled.
+ *  This class implements the code needed to create a timestamp request and to insert
+ *  a timestamp reply into a DICOM dataset, but not the protocol for actually
+ *  interacting with a timestamp authority.
+ *  @remark this class is only available if DCMTK is compiled with OpenSSL support enabled.
  */
 class DCMTK_DCMSIGN_EXPORT SiTimeStamp
-{    
+{
 public:
 
   /// default constructor
-  SiTimeStamp() { }
-  
+  SiTimeStamp();
+
   /// destructor
-  virtual ~SiTimeStamp() { }
+  virtual ~SiTimeStamp();
 
   /** takes a block of raw data and requests a time stamp for this raw data.
    *  @param inputData pointer to raw data
@@ -52,16 +65,248 @@ public:
    *  @return status code
    */
   virtual OFCondition stamp(
-    const unsigned char *inputData, 
+    const unsigned char *inputData,
     unsigned long inputDataSize) = 0;
 
+  /** reads the current timestamp from an item of the Digital Signatures Sequence
+   *  and creates a timestamp ticket object.
+   *  @param item item of the DigitalSignatureSQ from which the timestamp is read
+   *  @return status code
+   */
+  virtual OFCondition read(DcmItem& item);
+
   /** writes the current timestamp into an item of the Digital Signatures Sequence
    *  and creates the timestamp type information in the item.
    *  @param item item of the DigitalSignatureSQ to which the timestamp is written
-   *  @return dcmdata OFCondition status code
+   *  @return status code
    */
   virtual OFCondition write(DcmItem& item) = 0;
 
+  /** set the requested policy OID to be included into the time stamp query
+   *  @param oid policy OID, NULL for no policy (which is the default).
+   */
+  virtual void setPolicyOID(const char *oid);
+
+  /** sets the flag controlling whether or not a nonce is included
+   *  into the timestamp query. Since a nonce is a protection against replay
+   *  attack, normally it should be included, and this is also the default.
+   *  @param nonce OFTrue if nonce should be included, OFFalse otherwise
+   */
+  virtual void setNonce(OFBool nonce);
+
+  /** sets the flag controlling whether the timestamp authority will be
+   *  requested to include its certificate into the timestamp reply.
+   *  A timestamp reply with certificate is easier to verify, as less
+   *  external key material is required, but somewhat larger.
+   *  Default is OFTrue;
+   *  @param creq OFTrue if certificate should be requested, OFFalse otherwise
+   */
+  virtual void setCertificateRequested(OFBool creq);
+
+  /** sets the message authentication code to be used for creating
+   *  the hash value in the timestamp query. Default is SHA256.
+   *  @param creq OFTrue if certificate should be requested, OFFalse otherwise
+   */
+  virtual void setMAC(E_MACType mac);
+
+  // methods that return the various attributes of a timestamp ticket
+
+  /** checks if this object contains a timestamp ticket info object
+   *  @return OFTrue if timestamp ticket info available, OFFalse otherwise
+   */
+  virtual OFBool have_tsinfo() const;
+
+  /** returns the timestamp ticket info version number
+   *  @return tsinfo version number if available, -1 otherwise
+   */
+  virtual long get_tsinfo_version() const;
+
+  /** returns the timestamp ticket info policy OID
+   *  @param oid upon return, contains the policy OID if available, an empty string otherwise
+   */
+  virtual void get_tsinfo_policy_oid(OFString& oid) const;
+
+  /** returns the timestamp ticket info MAC algorithm name
+   *  @param mac upon return, contains the MAC algorithm name if available, an empty string otherwise
+   */
+  virtual void get_tsinfo_imprint_algorithm_name(OFString& mac) const;
+
+  /** returns the timestamp ticket info serial number
+   *  @param serial upon return, contains the serial number if available, an empty string otherwise
+   */
+  virtual void get_tsinfo_serial_number(OFString& serial) const;
+
+  /** returns the timestamp ticket info nonce, if present
+   *  @param nonce upon return, contains the nonce if available, an empty string otherwise
+   */
+  virtual void get_tsinfo_nonce(OFString& nonce) const;
+
+  /** returns the timestamp ticket info timestamp authority (TSA) name, if present
+   *  @param tsa upon return, contains the TSA name if available, an empty string otherwise
+   */
+  virtual void get_tsinfo_tsa_name(OFString& tsa) const;
+
+  /** returns the timestamp ticket info ordering flag
+   *  @return OFTrue if timestamp ticket is present and contains an ordering flag with value "true", OFFalse otherwise
+   */
+  virtual OFBool get_tsinfo_ordering() const;
+
+  /** returns the timestamp ticket info accuracy, if present
+   *  @param accuracy upon return, contains the accuracy if available, an empty string otherwise
+   */
+  virtual void get_tsinfo_accuracy(OFString& accuracy) const;
+
+  /** returns the timestamp date/time information, if present
+   *  @param ts upon return, contains the timestamp date/time information, an empty string otherwise
+   */
+  virtual void get_tsinfo_timestamp(OFString& ts) const;
+
+  /** returns the number of extensions in the timestamp ticket
+   *  @return number of extensions in the timestamp ticket
+   */
+  virtual int get_tsinfo_numextensions() const;
+
+  /** returns one timestamp extension, if present
+   *  @param ext upon return, contains the timestamp extension if present, an empty string otherwise
+   *  @param idx number of the extension, 0 <= idx < get_tsinfo_numextensions().
+   */
+  virtual void get_tsinfo_extension(OFString& ext, int idx) const;
+
+  /** this method performs the following functions:
+   *  - it checks if there is one and only one signer.
+   *  - it identifies the signer certificate (which may be embedded in the timestamp, or loaded in the SiCertificateVerifier store)
+   *  - it checks the extended key usage and key usage fields of the signer certificate
+   *  - it verifies the certificate path
+   *  - it checks if the certificate path meets the requirements of the
+   *    SigningCertificate ESS signed attribute.
+   *  - it verifies the signature value (against the imprint in the timestamp token
+   *  - it prints the contents of the signer certificate to the logger
+   *  @param cv container for the certificates used during verification
+   *  @return EC_Normal upon success, an error code otherwise.
+   */
+  virtual OFCondition verifyTSSignature(SiCertificateVerifier& cv);
+
+  /** Verify the timestamp token by checking that its imprint is
+   *  indeed a hash of the DICOM signature, that the version number
+   *  is as expected and that the TSA name, if provided in the timestamp
+   *  ticket structure, matches the name of the TSA given in the TSA
+   *  certificate.
+   *  @param cv container for the certificates used during verification
+   *  @param ditem item of the Digital Signatures Sequence containing the timestamp
+   *  @param cert certificate of the signer of the DICOM signature, used to check
+   *    the date/time of the timestamp against the validity period of the certificate
+   *  @return EC_Normal upon success, an error code otherwise.
+   */
+  virtual OFCondition verifyTSToken(
+    SiCertificateVerifier& cv,
+    DcmItem& ditem,
+    SiCertificate& cert);
+
+  /** returns an error string containing a textual description of the result
+   *  of the last call to verifyTSSignature() or verifyTSToken()
+   *  if that call returned SI_EC_TimestampSignatureVerificationFailed.
+   *  @param err text string returned in this parameter
+   */
+  void lastError(OFString& err) const;
+
+protected:
+
+  /** takes a block of raw data, computes a message digest and creates
+   *  a time stamp query object.
+   *  @param inputData pointer to raw data
+   *  @param inputDataSize length of raw data block in bytes
+   *  @return status code
+   */
+  virtual OFCondition create_ts_query(
+    const unsigned char *inputData,
+    unsigned long inputDataSize);
+
+  /** return pointer to timestamp query object, may be NULL.
+   *  @return pointer to timestamp query object, may be NULL.
+   */
+  virtual TS_REQ *getTSQ() { return tsq_; }
+
+  /** return pointer to timestamp response object, may be NULL.
+   *  @return pointer to timestamp response object, may be NULL.
+   */
+  virtual TS_RESP *getTSR() { return tsr_; }
+
+  /** return pointer to timestamp ticket object, may be NULL.
+   *  @return pointer to timestamp ticket object, may be NULL.
+   */
+  virtual PKCS7 *getTS() { return ts_; }
+
+  /** return pointer to timestamp ticket info object, may be NULL.
+   *  @return pointer to timestamp ticket info object, may be NULL.
+   */
+  virtual TS_TST_INFO *getTSInfo() { return tsinfo_; }
+
+  /** load timestamp query from file
+   *  @param fname filename, must not be NULL
+   *  @return status code
+   */
+  virtual OFCondition load_ts_query(const char *fname);
+
+  /** load timestamp response from file
+   *  @param fname filename, must not be NULL
+   *  @return status code
+   */
+  virtual OFCondition load_ts_response(const char *fname);
+
+  /** check consistency between timestamp query (if available), timestamp
+   *  response and DICOM digital signature.
+   *  @param tsq pointer to timestamp query, may be NULL
+   *  @param tsr pointer to timestamp response, must not be NULL
+   *  @param ditem item of the DigitalSignaturesSequence to which this timestamp belongs
+   *  @return status code
+   */
+  static OFCondition check_ts_response(
+    TS_REQ *tsq,
+    TS_RESP *tsr,
+    DcmItem& ditem);
+
+  /** insert timestamp token into DICOM dataset
+   *  The timestamp response must have been checked prior to this method call.
+   *  @param tsr pointer to timestamp response, must not be NULL
+   *  @param ditem item of the DigitalSignaturesSequence to which this timestamp is written
+   *  @return status code
+   */
+  static OFCondition write_ts_token(
+    TS_RESP *tsr,
+    DcmItem& ditem);
+
+private:
+
+  /// time stamping policy OID to be included in the time stamp query. Default is empty.
+  OFString tsq_policy_;
+
+  /// MAC algorithm for creating the hash key to be timestamped. Default is SHA-256.
+  E_MACType tsq_mac_;
+
+  /// Use a pseudo-random nonce in the time stamp query. Default is OFTrue.
+  OFBool tsq_use_nonce_;
+
+  /// Request the TSA certificate to be embedded into the time stamp reply. Default is OFTrue.
+  OFBool tsq_certificate_requested_;
+
+  /// pointer to time stamp request object, may be NULL
+  TS_REQ *tsq_;
+
+  /// pointer to time stamp response object, may be NULL
+  TS_RESP *tsr_;
+
+  /// pointer to time stamp ticket object, may be NULL
+  PKCS7 *ts_;
+
+  /// pointer to time stamp ticket info object (extracted from the timestamp ticket), may be NULL
+  TS_TST_INFO *tsinfo_;
+
+  /// OpenSSL X.509 certificate verification error code for the last operation
+  long errorCode_;
+
+  /// error string for the last operation, valid if errorCode_ < 0
+  const char *errorString_;
+
 };
 
 #endif
index bb99401d3b04e58b6324d21ac45b73fea8f7a03c..03c57efe0701837d06c35b16d90584632a84185a 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #include "dcmtk/ofstd/ofcond.h"
 #include "dcmtk/oflog/oflog.h"
 #include "dcmtk/dcmsign/sidefine.h"
+#include "dcmtk/dcmsign/sitypes.h"
 
 /*
 ** Logging
 */
 
-extern DCMTK_DCMSIGN_EXPORT OFLogger DCM_dcmsignLogger;
+extern DCMTK_DCMSIGN_EXPORT OFLogger dcmsignLogger;
 
-#define DCMSIGN_TRACE(msg) OFLOG_TRACE(DCM_dcmsignLogger, msg)
-#define DCMSIGN_DEBUG(msg) OFLOG_DEBUG(DCM_dcmsignLogger, msg)
-#define DCMSIGN_INFO(msg)  OFLOG_INFO(DCM_dcmsignLogger, msg)
-#define DCMSIGN_WARN(msg)  OFLOG_WARN(DCM_dcmsignLogger, msg)
-#define DCMSIGN_ERROR(msg) OFLOG_ERROR(DCM_dcmsignLogger, msg)
-#define DCMSIGN_FATAL(msg) OFLOG_FATAL(DCM_dcmsignLogger, msg)
+#define DCMSIGN_TRACE(msg) OFLOG_TRACE(dcmsignLogger, msg)
+#define DCMSIGN_DEBUG(msg) OFLOG_DEBUG(dcmsignLogger, msg)
+#define DCMSIGN_INFO(msg)  OFLOG_INFO(dcmsignLogger, msg)
+#define DCMSIGN_WARN(msg)  OFLOG_WARN(dcmsignLogger, msg)
+#define DCMSIGN_ERROR(msg) OFLOG_ERROR(dcmsignLogger, msg)
+#define DCMSIGN_FATAL(msg) OFLOG_FATAL(dcmsignLogger, msg)
 
 
 // DICOM defined terms for MAC algorithms, certificate and timestamp types
@@ -56,7 +57,6 @@ extern DCMTK_DCMSIGN_EXPORT OFLogger DCM_dcmsignLogger;
 #define SI_DEFTERMS_SHA384    "SHA384"
 #define SI_DEFTERMS_SHA512    "SHA512"
 
-
 // include this file in doxygen documentation
 
 /** @file sitypes.h
@@ -79,6 +79,9 @@ enum E_KeyType
   /// DH key
   EKT_DH,
 
+  /// EC key
+  EKT_EC,
+
   /// no key present
   EKT_none
 };
@@ -109,84 +112,185 @@ enum E_MACType
   EMT_SHA512
 };
 
+/** signature verification policy
+ *  @remark this enum is only available if DCMTK is compiled with
+ *  OpenSSL support enabled.
+ */
+enum E_SignatureVerificationPolicy
+{
+  /// verify signatures if present, pass otherwise
+  ESVP_verifyIfPresent,
+
+  /// fail if no signature is present at all but do not check any signature profile
+  ESVP_requireSignature,
+
+  /// fail if no valid creator RSA signature is present on the main dataset level
+  ESVP_requireCreatorRSASignature,
+
+  /// fail if no valid authorization RSA signature is present on the main dataset level
+  ESVP_requireAuthorizationRSASignature,
+
+  /// fail if no valid SR RSA signature is present on the main dataset level
+  ESVP_requireSRRSASignature
+};
+
+/** verification policy for certified timestamps attached to signatures
+ *  @remark this enum is only available if DCMTK is compiled with
+ *  OpenSSL support enabled.
+ */
+enum E_TimestampVerificationPolicy
+{
+  /// verify timestamp if present, pass otherwise
+  ETVP_verifyTSIfPresent,
+
+  /// ignore certified timestamp even if present
+  ETVP_ignoreTS,
+
+  /// fail if signature does not contain a certified timestamp
+  ETVP_requireTS,
+
+};
+
+
 /*
  * specific error conditions for module dcmsign
  */
 
 /// object initialization failed
-/// @remark this constant is only available if DCMTK is compiled with
-/// OpenSSL support enabled.
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
 extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_InitializationFailed;
 
 /// an OpenSSL call has failed
-/// @remark this constant is only available if DCMTK is compiled with
-/// OpenSSL support enabled.
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
 extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_OpenSSLFailure;
 
 /// file cannot be read
-/// @remark this constant is only available if DCMTK is compiled with
-/// OpenSSL support enabled.
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
 extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_CannotRead;
 
 /// unable to use the selected transfer syntax for MAC computation
-/// @remark this constant is only available if DCMTK is compiled with
-/// OpenSSL support enabled.
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
 extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_WrongTransferSyntax;
 
 /// no more MAC ID numbers available
-/// @remark this constant is only available if DCMTK is compiled with
-/// OpenSSL support enabled.
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
 extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_MacIDsExhausted;
 
 /// certificate and private key do not match
-/// @remark this constant is only available if DCMTK is compiled with
-/// OpenSSL support enabled.
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
 extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_CertificateDoesNotMatchPrivateKey;
 
 /// MAC algorithm not allowed for the current security profile
-/// @remark this constant is only available if DCMTK is compiled with
-/// OpenSSL support enabled.
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
 extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_MacDoesNotMatchProfile;
 
 /// Signature algorithm not allowed for the current security profile
-/// @remark this constant is only available if DCMTK is compiled with
-/// OpenSSL support enabled.
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
 extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_AlgorithmDoesNotMatchProfile;
 
 /// Transfer syntax not allowed for the current security profile
-/// @remark this constant is only available if DCMTK is compiled with
-/// OpenSSL support enabled.
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
 extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_TransferSyntaxDoesNotMatchProfile;
 
-/** signature verification failed because the certificate is missing
- *  or cannot be read (e.g. unsupported format)
- *  @remark this constant is only available if DCMTK is compiled with
- *  OpenSSL support enabled.
- */
+/// Dataset is not suitable for the current security profile (e.g. wrong SOP class)
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_DatasetDoesNotMatchProfile;
+
+/// signature verification failed because the certificate is missing or cannot be read (e.g. unsupported format)
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
 extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_VerificationFailed_NoCertificate;
 
 /// signature verification failed because the corresponding MAC parameters item could not be found or is incomplete
-/// @remark this constant is only available if DCMTK is compiled with
-/// OpenSSL support enabled.
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
 extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_VerificationFailed_NoMAC;
 
 /// signature verification failed because the corresponding signature item is incomplete
-/// @remark this constant is only available if DCMTK is compiled with
-/// OpenSSL support enabled.
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
 extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_VerificationFailed_NoSignature;
 
 /// signature verification failed because the MAC algorithm is not supported
-/// @remark this constant is only available if DCMTK is compiled with
-/// OpenSSL support enabled.
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
 extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_VerificationFailed_UnsupportedMACAlgorithm;
 
 /// signature verification failed because the signature is invalid (document corrupted)
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
 extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_VerificationFailed_Corrupted;
 
 /// signature verification failed because the certificate was issued by an untrusted (unknown) CA
-/// @remark this constant is only available if DCMTK is compiled with
-/// OpenSSL support enabled.
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
 extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_VerificationFailed_NoTrust;
 
+/// unsupported MAC algorithm specified
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_UnsupportedMAC;
+
+/// invalid object identifier (OID) string
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_InvalidOID;
+
+/// unable to write time stamp query file
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_CannotWriteTSQ;
+
+/// verification of timestamp response message failed
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_InvalidTSR;
+
+/// signature verification failed because DataElementsSigned is missing or incorrect
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_VerificationFailed_NoDataElementsSigned;
+
+/// List of data elements signed does not match the profile requirements
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_DataElementsSignedDoesNotMatchProfile;
+
+/// desired signature location item not found
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_ItemLocationNotFound;
+
+/// unknown certified timestamp type
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_UnknownTimestampType;
+
+/// certified timestamp in dataset cannot be read
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_InvalidTimestamp;
+
+/// filetype is unknown (neither PEM nor DER)
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_InvalidFiletype;
+
+/// signature verification of the certified timestamp failed
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_TimestampSignatureVerificationFailed;
+
+/// signature verification failed because the certificate was already expired at the signature create date
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_VerificationFailed_CertExpiredAtSignature;
+
+/// signature verification failed because the certificate was not yet valid at signature creation date
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_VerificationFailed_CertNotYetValidAtSig;
+
+/// list of attributes to be signed contains attribute that is not signable
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_AttributeNotSignable;
+
+/// signature verification failed because the signature contains an attribute that is not signable
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_VerificationFailed_AttributeNotSignable;
+
+/// selected dataset or item is empty, nothing to sign
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_DatasetEmpty;
+
+/// cannot create signature for current signature profile: required attributes missing
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_RequiredAttributeMissing;
+
+/// cannot handle ECDSA signatures because OpenSSL was compiled without elliptic curve support
+/// @remark this constant is only available if DCMTK is compiled with OpenSSL support enabled.
+extern DCMTK_DCMSIGN_EXPORT const OFConditionConst SI_EC_EllipticCurveNotSupported;
+
 #endif
 #endif
index d38128105b795351f65cffe6b89524ec5cabe70f..db078fe1283c6ee207987bc6e7217d1c63d172ea 100644 (file)
@@ -1,5 +1,9 @@
 # create library from source files
-DCMTK_ADD_LIBRARY(dcmdsig dcsignat siautopr sibrsapr sicert sicertvf sicreapr sidsa simaccon simd5 sinullpr siprivat siripemd sirsa sisha1 sisprof sitypes sisha256 sisha384 sisha512)
+DCMTK_ADD_LIBRARY(
+  dcmdsig dcsighlp dcsignat siautopr sibrsapr sicert sicertvf sicreapr
+  sidsa siecdsa simaccon simd5 sinullpr siprivat sipurpos siripemd sirsa
+  sisha1 sisprof sisrpr sisrvpr sitstamp sitypes sisha256 sisha384
+  sisha512 sitsfs)
 
 DCMTK_TARGET_LINK_MODULES(dcmdsig ofstd dcmdata)
 DCMTK_TARGET_LINK_LIBRARIES(dcmdsig ${OPENSSL_LIBS})
index 5e03274a9b349a404be3ff0bfae764d226d0c6ce..e60234d7b65790d9935bd666f4a90fc6eefa2195 100644 (file)
@@ -1,3 +1,74 @@
+dcsighlp.o: dcsighlp.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmsign/dcsighlp.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../include/dcmtk/dcmsign/sidefine.h ../include/dcmtk/dcmsign/sipurpos.h \
+ ../include/dcmtk/dcmsign/sitypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdicent.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdict.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dchashdi.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
+ ../include/dcmtk/dcmsign/dcsignat.h ../include/dcmtk/dcmsign/sicert.h \
+ ../include/dcmtk/dcmsign/sicertvf.h ../include/dcmtk/dcmsign/sisprof.h \
+ ../include/dcmtk/dcmsign/sitsfs.h ../include/dcmtk/dcmsign/sitstamp.h \
+ ../include/dcmtk/dcmsign/sicreapr.h ../include/dcmtk/dcmsign/sibrsapr.h \
+ ../include/dcmtk/dcmsign/siautopr.h ../include/dcmtk/dcmsign/sisrvpr.h \
+ ../include/dcmtk/dcmsign/sisrpr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexit.h
 dcsignat.o: dcsignat.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmsign/dcsignat.h ../include/dcmtk/dcmsign/sitypes.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
@@ -40,6 +111,7 @@ dcsignat.o: dcsignat.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../include/dcmtk/dcmsign/sipurpos.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../ofstd/include/dcmtk/ofstd/offile.h \
@@ -76,7 +148,7 @@ dcsignat.o: dcsignat.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmsign/siripemd.h ../include/dcmtk/dcmsign/sisha1.h \
  ../include/dcmtk/dcmsign/sisha256.h ../include/dcmtk/dcmsign/sisha384.h \
  ../include/dcmtk/dcmsign/sisha512.h ../include/dcmtk/dcmsign/sisprof.h \
- ../include/dcmtk/dcmsign/sitstamp.h
+ ../include/dcmtk/dcmsign/sitstamp.h ../include/dcmtk/dcmsign/sitsfs.h
 siautopr.o: siautopr.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmsign/siautopr.h ../include/dcmtk/dcmsign/sibrsapr.h \
  ../include/dcmtk/dcmsign/sisprof.h ../include/dcmtk/dcmsign/sitypes.h \
@@ -113,7 +185,7 @@ siautopr.o: siautopr.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../include/dcmtk/dcmsign/sidefine.h \
+ ../include/dcmtk/dcmsign/sidefine.h ../include/dcmtk/dcmsign/sipurpos.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
@@ -121,7 +193,20 @@ siautopr.o: siautopr.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h
 sibrsapr.o: sibrsapr.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmsign/sibrsapr.h ../include/dcmtk/dcmsign/sisprof.h \
  ../include/dcmtk/dcmsign/sitypes.h \
@@ -158,7 +243,7 @@ sibrsapr.o: sibrsapr.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../include/dcmtk/dcmsign/sidefine.h \
+ ../include/dcmtk/dcmsign/sidefine.h ../include/dcmtk/dcmsign/sipurpos.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
@@ -204,6 +289,7 @@ sicert.o: sicert.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
  ../include/dcmtk/dcmsign/sidefine.h ../include/dcmtk/dcmsign/sirsa.h \
  ../include/dcmtk/dcmsign/sialgo.h ../include/dcmtk/dcmsign/sidsa.h \
+ ../include/dcmtk/dcmsign/siecdsa.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
@@ -228,7 +314,10 @@ sicert.o: sicert.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcbytstr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrobow.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h
 sicertvf.o: sicertvf.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmsign/sicert.h ../include/dcmtk/dcmsign/sitypes.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
@@ -301,7 +390,7 @@ sicreapr.o: sicreapr.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../include/dcmtk/dcmsign/sidefine.h \
+ ../include/dcmtk/dcmsign/sidefine.h ../include/dcmtk/dcmsign/sipurpos.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
@@ -309,7 +398,20 @@ sicreapr.o: sicreapr.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
  ../../ofstd/include/dcmtk/ofstd/ofthread.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
- ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h
 sidsa.o: sidsa.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmsign/sidsa.h ../include/dcmtk/dcmsign/sialgo.h \
  ../include/dcmtk/dcmsign/sitypes.h \
@@ -348,6 +450,44 @@ sidsa.o: sidsa.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
  ../include/dcmtk/dcmsign/sidefine.h ../include/dcmtk/dcmsign/sicert.h \
  ../include/dcmtk/dcmsign/siprivat.h
+siecdsa.o: siecdsa.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmsign/siecdsa.h ../include/dcmtk/dcmsign/sialgo.h \
+ ../include/dcmtk/dcmsign/sitypes.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../include/dcmtk/dcmsign/sidefine.h ../include/dcmtk/dcmsign/sicert.h \
+ ../include/dcmtk/dcmsign/siprivat.h
 simaccon.o: simaccon.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmsign/simaccon.h ../include/dcmtk/dcmsign/sitypes.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
@@ -488,7 +628,7 @@ sinullpr.o: sinullpr.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../include/dcmtk/dcmsign/sidefine.h \
+ ../include/dcmtk/dcmsign/sidefine.h ../include/dcmtk/dcmsign/sipurpos.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
@@ -532,7 +672,64 @@ siprivat.o: siprivat.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
  ../include/dcmtk/dcmsign/sidefine.h ../include/dcmtk/dcmsign/sirsa.h \
  ../include/dcmtk/dcmsign/sialgo.h ../include/dcmtk/dcmsign/sidsa.h \
- ../include/dcmtk/dcmsign/sicert.h
+ ../include/dcmtk/dcmsign/siecdsa.h ../include/dcmtk/dcmsign/sicert.h
+sipurpos.o: sipurpos.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmsign/sipurpos.h ../include/dcmtk/dcmsign/sidefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../include/dcmtk/dcmsign/sitypes.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h
 siripemd.o: siripemd.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmsign/siripemd.h ../include/dcmtk/dcmsign/simac.h \
  ../include/dcmtk/dcmsign/sitypes.h \
@@ -801,7 +998,7 @@ sisprof.o: sisprof.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
- ../include/dcmtk/dcmsign/sidefine.h \
+ ../include/dcmtk/dcmsign/sidefine.h ../include/dcmtk/dcmsign/sipurpos.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
@@ -824,7 +1021,253 @@ sisprof.o: sisprof.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrat.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../include/dcmtk/dcmsign/simac.h ../include/dcmtk/dcmsign/sialgo.h
+ ../include/dcmtk/dcmsign/simac.h ../include/dcmtk/dcmsign/sialgo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h
+sisrpr.o: sisrpr.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmsign/sisrpr.h ../include/dcmtk/dcmsign/sibrsapr.h \
+ ../include/dcmtk/dcmsign/sisprof.h ../include/dcmtk/dcmsign/sitypes.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../include/dcmtk/dcmsign/sidefine.h ../include/dcmtk/dcmsign/sipurpos.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h
+sisrvpr.o: sisrvpr.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmsign/sisrvpr.h ../include/dcmtk/dcmsign/sisrpr.h \
+ ../include/dcmtk/dcmsign/sibrsapr.h ../include/dcmtk/dcmsign/sisprof.h \
+ ../include/dcmtk/dcmsign/sitypes.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../include/dcmtk/dcmsign/sidefine.h ../include/dcmtk/dcmsign/sipurpos.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h
+sitsfs.o: sitsfs.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmsign/sitsfs.h ../include/dcmtk/dcmsign/sitstamp.h \
+ ../include/dcmtk/dcmsign/sitypes.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../include/dcmtk/dcmsign/sidefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcfilefo.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h
+sitstamp.o: sitstamp.cc ../../config/include/dcmtk/config/osconfig.h \
+ ../include/dcmtk/dcmsign/sitstamp.h ../include/dcmtk/dcmsign/sitypes.h \
+ ../../ofstd/include/dcmtk/ofstd/oftypes.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcast.h \
+ ../../ofstd/include/dcmtk/ofstd/ofexport.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstream.h \
+ ../../ofstd/include/dcmtk/ofstd/ofcond.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstring.h \
+ ../../oflog/include/dcmtk/oflog/oflog.h \
+ ../../oflog/include/dcmtk/oflog/logger.h \
+ ../../oflog/include/dcmtk/oflog/config.h \
+ ../../oflog/include/dcmtk/oflog/config/defines.h \
+ ../../oflog/include/dcmtk/oflog/helpers/threadcf.h \
+ ../../oflog/include/dcmtk/oflog/loglevel.h \
+ ../../ofstd/include/dcmtk/ofstd/ofvector.h \
+ ../../oflog/include/dcmtk/oflog/tstring.h \
+ ../../oflog/include/dcmtk/oflog/tchar.h \
+ ../../oflog/include/dcmtk/oflog/spi/apndatch.h \
+ ../../oflog/include/dcmtk/oflog/appender.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmem.h \
+ ../../ofstd/include/dcmtk/ofstd/ofutil.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../ofstd/include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../../oflog/include/dcmtk/oflog/layout.h \
+ ../../oflog/include/dcmtk/oflog/streams.h \
+ ../../oflog/include/dcmtk/oflog/helpers/pointer.h \
+ ../../oflog/include/dcmtk/oflog/thread/syncprim.h \
+ ../../oflog/include/dcmtk/oflog/spi/filter.h \
+ ../../oflog/include/dcmtk/oflog/helpers/lockfile.h \
+ ../../oflog/include/dcmtk/oflog/spi/logfact.h \
+ ../../oflog/include/dcmtk/oflog/logmacro.h \
+ ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
+ ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../include/dcmtk/dcmsign/sidefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdeftag.h \
+ ../include/dcmtk/dcmsign/simd5.h ../include/dcmtk/dcmsign/simac.h \
+ ../include/dcmtk/dcmsign/siripemd.h ../include/dcmtk/dcmsign/sisha1.h \
+ ../include/dcmtk/dcmsign/sisha256.h ../include/dcmtk/dcmsign/sisha384.h \
+ ../include/dcmtk/dcmsign/sisha512.h ../include/dcmtk/dcmsign/sicert.h \
+ ../include/dcmtk/dcmsign/sicertvf.h ../include/dcmtk/dcmsign/dcsignat.h \
+ ../include/dcmtk/dcmsign/sipurpos.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdatime.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h
 sitypes.o: sitypes.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/dcmsign/sitypes.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
index 4576b165a54d77531f50d4643efff558322edbaa..511a340c3740be984fc4a78661cd249ce4b6e669 100644 (file)
@@ -21,9 +21,10 @@ LOCALDEFS =
 
 objs = dcsignat.o sicert.o sidsa.o simd5.o siprivat.o sirsa.o sisprof.o \
        siautopr.o sicreapr.o simaccon.o sinullpr.o siripemd.o sisha1.o \
-       sitypes.o sicertvf.o sibrsapr.o sisha256.o sisha384.o sisha512.o
-library = libdcmdsig.$(LIBEXT)
+       sitypes.o sicertvf.o sibrsapr.o sisha256.o sisha384.o sisha512.o siecdsa.o \
+       sisrpr.o sisrvpr.o sipurpos.o dcsighlp.o sitstamp.o sitsfs.o
 
+library = libdcmdsig.$(LIBEXT)
 
 all: $(library)
 
diff --git a/dcmsign/libsrc/dcsighlp.cc b/dcmsign/libsrc/dcsighlp.cc
new file mode 100644 (file)
index 0000000..ff9f966
--- /dev/null
@@ -0,0 +1,984 @@
+/*
+ *
+ *  Copyright (C) 2000-2020, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmsign
+ *
+ *  Author: Marco Eichelberg
+ *
+ *  Purpose:
+ *    classes: DcmSignatureHelper
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#ifdef WITH_OPENSSL
+
+#include "dcmtk/dcmsign/dcsighlp.h"
+#include "dcmtk/dcmdata/dcdeftag.h" /* for attribute tag constants */
+#include "dcmtk/dcmdata/dcdicent.h" /* for class DcmDictEntry */
+#include "dcmtk/dcmdata/dcdict.h"   /* for class DcmDataDictionary */
+#include "dcmtk/dcmdata/dcitem.h"   /* for class DcmItem */
+#include "dcmtk/dcmdata/dcsequen.h" /* for class DcmSequenceOfItems */
+#include "dcmtk/dcmdata/dcvrat.h"   /* for class DcmAttributeTag */
+#include "dcmtk/dcmsign/dcsignat.h" /* for class DcmSignature */
+#include "dcmtk/dcmsign/sicert.h"   /* for class SiCertificate */
+#include "dcmtk/dcmsign/sicertvf.h" /* for class SiCertificateVerifier */
+#include "dcmtk/dcmsign/sisprof.h"  /* for class SiSecurityProfile */
+#include "dcmtk/dcmsign/sitsfs.h"   /* for class SiTimeStampFS */
+#include "dcmtk/dcmsign/sitypes.h"  /* for logger macros */
+#include "dcmtk/dcmsign/sicreapr.h" /* for class SiCreatorProfile */
+#include "dcmtk/dcmsign/siautopr.h" /* for class SiAuthorizationProfile */
+#include "dcmtk/dcmsign/sisrvpr.h"  /* for class SiStructuredReportingVerificationProfile */
+#include "dcmtk/ofstd/ofexit.h"     /* for common exit codes */
+#include "dcmtk/dcmsign/siexit.h"   /* for dcmsign specific exit codes */
+
+
+DcmSignatureHelper::DcmSignatureHelper()
+{
+}
+
+DcmSignatureHelper::~DcmSignatureHelper()
+{
+}
+
+int DcmSignatureHelper::readNextToken(const char *c, int& pos, DcmTagKey& key, Uint32& idx)
+{
+  OFString aString;
+  int lpos = pos;
+  int spos = 0;
+  while(isspace(OFstatic_cast(unsigned char, c[lpos]))) ++lpos; // ignore leading space
+
+  if (c[lpos]=='\0') return -1; // EOF
+  if (c[lpos]=='.')
+  {
+    ++pos;
+    return 3; // period
+  }
+  if (c[lpos]=='[')
+  {
+    spos = ++lpos;
+    while ((c[lpos] >= '0')&&(c[lpos] <= '9')) ++lpos;
+    if (c[lpos] != ']') return 0; // parse error
+    unsigned long newindex = 0;
+    if (1 != sscanf(c+spos,"%lu", &newindex)) return 0; // parse error
+    idx = OFstatic_cast(Uint32, newindex);
+    pos = ++lpos;
+    return 2; // index
+  }
+  if (c[lpos]=='(')
+  {
+    spos = ++lpos;
+    while ((c[lpos] != ')')&&(c[lpos] != '\0')) ++lpos;
+    if (c[lpos] != ')') return 0; // parse error
+    unsigned int group=0;
+    unsigned int elem=0;
+    if (2 != sscanf(c+spos,"%x,%x", &group, &elem)) return 0; // parse error
+    key = DcmTagKey(group,elem);
+    pos = ++lpos;
+    return 1; // tag key
+  }
+  spos = lpos;
+  while ( ((c[lpos] >= 'a')&&(c[lpos] <= 'z')) || ((c[lpos] >= 'A')&&(c[lpos] <= 'Z')) || ((c[lpos] >= '0')&&(c[lpos] <= '9'))) ++lpos;
+  aString.append(c + spos, (lpos-spos));
+  const DcmDataDictionary& globalDataDict = dcmDataDict.rdlock();
+  const DcmDictEntry *dicent = globalDataDict.findEntry(aString.c_str());
+  if (dicent)
+  {
+    key = dicent->getKey();
+    dcmDataDict.rdunlock();
+    pos = lpos;
+    return 1; // tag key;
+  }
+  dcmDataDict.rdunlock();
+  DCMSIGN_ERROR("attribute name '" << aString.c_str() << "' unknown.");
+  return 0; // parse error
+}
+
+
+char *DcmSignatureHelper::readTextFile(const char *filename)
+{
+  char *result = NULL;
+  FILE *file = fopen(filename, "rb");
+  if (file)
+  {
+    fseek(file, 0, SEEK_END);
+    long numBytes = ftell(file);
+    fseek(file, 0, SEEK_SET);
+    result = new char[numBytes+1];
+    if (result)
+    {
+      result[numBytes] = '\0'; // ensure zero termination of text field
+      if (OFstatic_cast(size_t, numBytes) != fread(result, 1, OFstatic_cast(size_t, numBytes), file))
+      {
+        DCMSIGN_WARN("read error in file " << filename);
+        delete[] result;
+        result = NULL;
+      }
+    }
+    fclose(file);
+  } else {
+    DCMSIGN_ERROR("file not found: " << filename);
+  }
+  return result;
+}
+
+
+int DcmSignatureHelper::parseTextFile(const char *filename, DcmAttributeTag& tagList)
+{
+  char *c=readTextFile(filename);
+  if (c==NULL) return EXITCODE_CANNOT_READ_TAG_FILE; // bail out
+  int position = 0;
+  int token = 0;
+  Uint32 idx = 0;
+  DcmTagKey key;
+  int result = EXITCODE_NO_ERROR;
+  do
+  {
+    token = readNextToken(c, position, key, idx);
+    if (token == 1) // we have read a tag key
+    {
+      if (EC_Normal != tagList.putTagVal(key, tagList.getVM()))
+      {
+        result = EXITCODE_SYNTAX_ERROR_IN_TAG_FILE;
+        token = -1;
+      }
+    }
+    else if (token >= 0)
+    {
+      DCMSIGN_ERROR("parse error in text file '" << filename << "'");
+      result = EXITCODE_SYNTAX_ERROR_IN_TAG_FILE;
+      token = -1;
+    }
+  } while (token >= 0);
+  delete[] c;
+  return result;
+}
+
+
+OFBool DcmSignatureHelper::addTag(const char *c, DcmAttributeTag& tagList)
+{
+  OFBool result = OFFalse;
+  unsigned int group = 0xffff;
+  unsigned int elem = 0xffff;
+  if (sscanf(c, "%x,%x", &group, &elem ) != 2 )
+  {
+    /* it is a name */
+    const DcmDataDictionary& globalDataDict = dcmDataDict.rdlock();
+    const DcmDictEntry *dicent = globalDataDict.findEntry(c);
+    if (dicent)
+    {
+      if (EC_Normal == tagList.putTagVal(dicent->getKey(), tagList.getVM())) result = OFTrue;
+    }
+    dcmDataDict.rdunlock();
+  } else {
+    if (EC_Normal == tagList.putTagVal(DcmTagKey(group,elem), tagList.getVM())) result = OFTrue;
+  }
+  return result;
+}
+
+
+DcmItem *DcmSignatureHelper::locateItemforSignatureCreation(DcmItem& dataset, const char *location)
+{
+  DcmTagKey key;
+  Uint32 idx;
+  int pos = 0;
+  int token = 0;
+  int expected = 1;
+  OFBool finished = OFFalse;
+  DcmItem *result = &dataset;
+  DcmSequenceOfItems *sq = NULL;
+  DcmStack stack;
+  do
+  {
+    token = readNextToken(location, pos, key, idx);
+    if ((token != expected)&&(token != -1))
+    {
+      DCMSIGN_ERROR("parse error in item location string '" << location << "'");
+      return NULL;
+    }
+    if (token == -1)
+    {
+      if (! finished)
+      {
+        DCMSIGN_ERROR("item location string '" << location << "' incomplete.");
+        return NULL;
+      }
+      return result;
+    }
+    if (token == 1)
+    {
+      // we have read a tag key
+      stack.clear();
+      if (EC_Normal != result->search(key, stack, ESM_fromHere, OFFalse))
+      {
+        DCMSIGN_ERROR("attribute " << key << " not found in dataset (item location string is '" << location << "')");
+        return NULL;
+      }
+      if (stack.top()->ident() == EVR_SQ)
+      {
+        sq = OFstatic_cast(DcmSequenceOfItems *, (stack.top()));
+      } else {
+        DCMSIGN_ERROR("attribute " << key << " is not a sequence (item location string is '" << location << "')");
+        return NULL;
+      }
+      expected = 2;
+      finished = OFFalse;
+    }
+    else if (token == 2)
+    {
+      // we have read an index
+      if (sq == NULL)
+      {
+        DCMSIGN_ERROR("sequence not found in item location string '" << location << "'");
+        return NULL;
+      }
+      if (idx >= sq->card())
+      {
+        DCMSIGN_ERROR("sequence " << sq->getTag() << " only has " << sq->card()
+          << " items, cannot locate item " << idx << " (item location string is '" << location << "')");
+        return NULL;
+      }
+      result = sq->getItem(idx);
+      if (result == NULL)
+      {
+        DCMSIGN_ERROR("item not found in item location string '" << location << "'");
+        return NULL;
+      }
+      expected = 3;
+      finished = OFTrue;
+    }
+    else if (token == 3)
+    {
+      // we have read a period
+      expected = 1;
+      finished = OFFalse;
+    }
+  } while (token > 0);
+  return NULL;
+}
+
+
+void DcmSignatureHelper::printSignatureItemPosition(DcmStack& stack, OFString& str)
+{
+  str.clear();
+  DcmObject *elem = NULL;
+  DcmSequenceOfItems *sq = NULL;
+  unsigned long sqCard=0;
+  const char *tagname = NULL;
+  unsigned long m=0;
+  char buf[30];
+  if (stack.card() > 2)
+  {
+    // signature is located within a sequence
+    for (unsigned long l=stack.card()-2; l>0; --l) // loop over all elements except the stack top and bottom
+    {
+      elem = stack.elem(l);
+      if (elem)
+      {
+        if ((elem->ident() == EVR_item) && sq)
+        {
+          sqCard = sq->card();
+          for (m=0; m<sqCard; m++)
+          {
+            if (sq->getItem(m) == elem)
+            {
+              sprintf(buf, "[%lu]", m);
+              str.append(buf);
+            }
+          }
+        }
+        else
+        {
+          if (str.size() > 0) str.append(".");
+          sq = OFstatic_cast(DcmSequenceOfItems *, elem);
+          DcmTag currentTag(elem->getTag());
+          tagname = currentTag.getTagName();
+          if (tagname) str.append(tagname); else
+          {
+            sprintf(buf, "(%04x,%04x)", elem->getTag().getGroup(), elem->getTag().getElement());
+            str.append(buf);
+          }
+          if (elem->ident() == EVR_SQ) sq = OFstatic_cast(DcmSequenceOfItems *, elem); else sq = NULL;
+        }
+      }
+    }
+  } else {
+    // signature is located in the main dataset
+    str = "Main Dataset";
+  }
+}
+
+
+int DcmSignatureHelper::do_sign(
+  DcmItem *dataset,
+  SiPrivateKey& key,
+  SiCertificate& cert,
+  SiMAC *opt_mac,
+  SiSecurityProfile *opt_profile,
+  DcmAttributeTag *opt_tagList,
+  E_TransferSyntax opt_signatureXfer,
+  FILE *dumpFile,
+  SiSignaturePurpose::E_SignaturePurposeType opt_sigPurpose,
+  SiTimeStamp *timeStamp)
+{
+  OFCondition sicond = opt_profile->inspectSignatureDataset(*dataset);
+  if (sicond.good())
+  {
+    DcmSignature signer;
+    signer.attach(dataset);
+    signer.setDumpFile(dumpFile);
+    sicond = signer.createSignature(key, cert, *opt_mac, *opt_profile, opt_signatureXfer, opt_tagList, timeStamp, opt_sigPurpose);
+    signer.detach();
+  }
+
+  if (sicond.bad())
+  {
+    DCMSIGN_ERROR(sicond.text() << " while creating signature in main dataset");
+    return EXITCODE_SIGNATURE_CREATION_FAILED;
+  }
+  return EXITCODE_NO_ERROR;
+}
+
+
+int DcmSignatureHelper::do_sign_item(
+  DcmItem *dataset,
+  SiPrivateKey& key,
+  SiCertificate& cert,
+  SiMAC *opt_mac,
+  SiSecurityProfile *opt_profile,
+  DcmAttributeTag *opt_tagList,
+  const char *opt_location,
+  E_TransferSyntax opt_signatureXfer,
+  FILE *dumpFile,
+  SiSignaturePurpose::E_SignaturePurposeType opt_sigPurpose,
+  SiTimeStamp *timeStamp)
+{
+  OFCondition sicond = EC_Normal;
+  DcmItem *sigItem = locateItemforSignatureCreation(*dataset, opt_location);
+  if (sigItem == NULL) sicond = SI_EC_ItemLocationNotFound;
+  else
+  {
+    sicond = opt_profile->inspectSignatureDataset(*sigItem);
+    if (sicond.good())
+    {
+      DcmSignature signer;
+      signer.attach(sigItem);
+      signer.setDumpFile(dumpFile);
+      sicond = signer.createSignature(key, cert, *opt_mac, *opt_profile, opt_signatureXfer, opt_tagList, timeStamp, opt_sigPurpose);
+      signer.detach();
+    }
+  }
+
+  if (sicond.bad())
+  {
+    DCMSIGN_ERROR(sicond.text() << " while creating signature in item '" << opt_location << "'");
+    return EXITCODE_SIGNATURE_CREATION_FAILED;
+  }
+  return EXITCODE_NO_ERROR;
+}
+
+
+int DcmSignatureHelper::do_verify(
+    DcmItem *dataset,
+    SiCertificateVerifier& certVerifier,
+    E_SignatureVerificationPolicy verificationPolicy,
+    E_TimestampVerificationPolicy timestampPolicy)
+{
+  OFCondition sicond = EC_Normal;
+  DcmStack stack;
+  DcmSignature signer;
+  OFString aString;
+
+  // this counter counts the number of signatures found in the dataset
+  int counter = 0;
+
+  // this counter contains the number of signatures in the dataset
+  // that have failed validation
+  int corrupt_counter = 0;
+
+  unsigned long numSignatures = 0;
+  unsigned long l=0;
+  DcmItem *sigItem = DcmSignature::findFirstSignatureItem(*dataset, stack);
+
+  // this flag is set to true if we find any signature in the dataset
+  // that complies with the verification policy.
+  OFBool verificationPolicyFulfilled = OFFalse;
+  const char *verificationPolicyName = "(undefined)";
+  OFString s;
+
+  // for these verification policies, there is nothing to check,
+  // ESVP_requireSignature is checked elsewhere.
+  if ((verificationPolicy == ESVP_verifyIfPresent) ||
+      (verificationPolicy == ESVP_requireSignature))
+      verificationPolicyFulfilled = OFTrue;
+
+  while (sigItem)
+  {
+    signer.attach(sigItem);
+    numSignatures = signer.numberOfSignatures();
+    for (l=0; l<numSignatures; l++)
+    {
+      OFBool cert_expiry = OFFalse;
+      OFBool checkTimestamp = OFFalse;
+      if (EC_Normal == signer.selectSignature(l))
+      {
+        ++counter;
+        printSignatureDetails(signer, stack, counter);
+
+        if (dcmsignLogger.isEnabledFor(OFLogger::INFO_LOG_LEVEL))
+          aString = "  Signature Verification      : ";
+          else aString = "  Signature Verification : ";
+
+        // verify signature profile
+        switch (verificationPolicy)
+        {
+          case ESVP_requireCreatorRSASignature:
+            {
+              verificationPolicyName = "Creator RSA Signature";
+              SiCreatorProfile sprofCr;
+              if (! verificationPolicyFulfilled) verificationPolicyFulfilled = signer.verifySignatureProfile(sprofCr).good();
+            }
+            break;
+          case ESVP_requireAuthorizationRSASignature:
+            {
+              verificationPolicyName = "Authorization RSA Signature";
+              SiAuthorizationProfile sprofAu;
+              if (! verificationPolicyFulfilled) verificationPolicyFulfilled = signer.verifySignatureProfile(sprofAu).good();
+            }
+            break;
+          case ESVP_requireSRRSASignature:
+            {
+              // there are two types of possible matches here:
+              // either the dataset is an UNVERIFIED SR and SiStructuredReportingProfile matches,
+              // or the dataset is a VERIFIED SR and SiStructuredReportingVerificationProfile matches.
+              // We select the profile based on the value of VerificationFlag on main dataset level.
+              verificationPolicyName = "SR RSA Signature";
+              if (! verificationPolicyFulfilled)
+              {
+                if (dataset->findAndGetOFString(DCM_VerificationFlag, s).good() && (s == "VERIFIED"))
+                {
+                  SiStructuredReportingVerificationProfile sprofSRV;
+                  verificationPolicyFulfilled = signer.verifySignatureProfile(sprofSRV).good();
+                }
+                else
+                {
+                  SiStructuredReportingProfile sprofSR;
+                  verificationPolicyFulfilled = signer.verifySignatureProfile(sprofSR).good();
+                }
+              }
+            }
+            break;
+          case ESVP_verifyIfPresent:
+          case ESVP_requireSignature:
+            break;
+          // There is deliberately no default here because if we extend
+          // the enum then we will have to extend this code.
+        }
+
+        // first verify if the signature matches the dataset
+        sicond = signer.verifyCurrent();
+        if (sicond.good())
+        {
+          // now check if we can successfully verify the signer's certificate
+          SiCertificate *cert = signer.getCurrentCertificate();
+          if (cert)
+          {
+            // print a warning if we have a weak (i.e. too short) key in the certificate
+            cert->checkForWeakKey();
+
+            if (certVerifier.verifyCertificate(*cert).good())
+            {
+              DCMSIGN_WARN(aString << "OK");
+              checkTimestamp = OFTrue;
+            }
+            else
+            {
+              cert_expiry = certVerifier.lastErrorIsCertExpiry();
+              DCMSIGN_WARN(aString << "signature is OK but certificate verification failed: " << certVerifier.lastError());
+              corrupt_counter++;
+            }
+          }
+          else
+          {
+            DCMSIGN_WARN(aString << "failed, certificate empty or invalid");
+            corrupt_counter++;
+          }
+        } else {
+          DCMSIGN_WARN(aString << sicond.text());
+          corrupt_counter++;
+        }
+
+        // check certified timestamp (if any).
+        // We only do this if the signature verification has passed
+        // or if the signature is OK but the signer certificate has expired,
+        // which may be "healed" by a timestamp that is still valid
+        if (checkTimestamp || cert_expiry)
+        {
+          printTimestampDetails(signer, timestampPolicy);
+
+          SiTimeStamp *tstamp = signer.getCurrentTimestamp();
+          OFBool haveTS = (tstamp != NULL) && tstamp->have_tsinfo();
+          if (haveTS)
+          {
+            if (timestampPolicy != ETVP_ignoreTS)
+            {
+              // timestamp is present and according to our policy we should verify it
+              if (dcmsignLogger.isEnabledFor(OFLogger::INFO_LOG_LEVEL))
+                aString = "  Timestamp Verification      : ";
+                else aString = "  Timestamp Verification : ";
+
+              sicond = tstamp->verifyTSSignature(certVerifier);
+              if (sicond.good())
+              {
+                sicond = tstamp->verifyTSToken(certVerifier, *signer.getSelectedSignatureItem(), *signer.getCurrentCertificate());
+                if (sicond.good())
+                {
+                  if (cert_expiry)
+                  {
+                    // we have an expired signature but a timestamp that is still valid,
+                    // which means that the timestamp "heals" the failed signature verification
+                    corrupt_counter--;
+                    DCMSIGN_WARN(aString << "OK, extends validity period of expired signature.");
+                  }
+                  else
+                  {
+                    DCMSIGN_WARN(aString << "OK");
+                  }
+                }
+                else
+                {
+                  OFString errString;
+                  tstamp->lastError(errString); // check if we have an OpenSSL error message
+                  if (errString.length() == 0) errString = sicond.text(); // use DCMTK error message otherwise
+                  DCMSIGN_WARN(aString << "timestamp signature verification failed: " << errString);
+                  if (!cert_expiry) corrupt_counter++; // if cert_expiry is true, the counter has already been increased
+                }
+              }
+              else
+              {
+                OFString errString;
+                tstamp->lastError(errString);
+                DCMSIGN_WARN(aString << "timestamp signature verification failed: " << errString);
+                if (!cert_expiry) corrupt_counter++; // if cert_expiry is true, the counter has already been increased
+              }
+            }
+          }
+          else
+          {
+            // no timestamp present. Check if this is a problem.
+            if (timestampPolicy == ETVP_requireTS)
+            {
+              DCMSIGN_WARN("  Certified timestamp : absent, but required by timestamp policy");
+              if (!cert_expiry) corrupt_counter++; // if cert_expiry is true, the counter has already been increased
+            }
+          }
+        } // if (checkTimestamp)
+      } // if (EC_Normal == signer.selectSignature(l))
+    } // for (l=0; l<numSignatures; l++)
+    signer.detach();
+    sigItem = DcmSignature::findNextSignatureItem(*dataset, stack);
+  } // while (sigItem)
+
+  if (counter == 0)
+  {
+    if (verificationPolicy == ESVP_verifyIfPresent)
+    {
+      DCMSIGN_WARN("no signatures found in dataset.");
+    }
+    else
+    {
+      // no signature present but according to the signature policy, we would have expected one
+      DCMSIGN_ERROR("no signatures found although required by the signature verification policy.");
+      return EXITCODE_NO_SIGNATURES_PRESENT;
+    }
+  }
+  else
+  {
+    DCMSIGN_INFO(counter << " signatures verified in dataset, " << corrupt_counter << " corrupted.");
+  }
+
+  if (! verificationPolicyFulfilled)
+  {
+    DCMSIGN_ERROR("No signature in this dataset fulfills the required " << verificationPolicyName << " signature policy");
+    return EXITCODE_SIGNATURE_VERIFICATION_POLICY;
+  }
+
+  // return non-zero if any verification has failed
+  return (corrupt_counter == 0 ? EXITCODE_NO_ERROR : EXITCODE_SIGNATURE_VERIFICATION_FAILED);
+}
+
+
+int DcmSignatureHelper::do_remove_all(DcmItem *dataset)
+{
+  OFCondition sicond = EC_Normal;
+  DcmSignature signer;
+  int counter = 0;
+  OFString aString;
+  DcmStack stack;
+  DcmItem *sigItem = DcmSignature::findFirstSignatureItem(*dataset, stack);
+  while (sigItem)
+  {
+    signer.attach(sigItem);
+    while (signer.numberOfSignatures() > 0)
+    {
+      ++counter;
+      if (EC_Normal == signer.selectSignature(0))
+      {
+        if (EC_Normal == signer.getCurrentSignatureUID(aString))
+          DCMSIGN_WARN("Signature #" << counter << " UID=" << aString);
+        else
+          DCMSIGN_WARN("Signature #" << counter << " UID=(unknown)");
+        printSignatureItemPosition(stack, aString);
+        DCMSIGN_WARN("  Location                    : " << aString);
+      }
+      sicond = signer.removeSignature(0);
+      if (sicond != EC_Normal)
+      {
+        DCMSIGN_ERROR(sicond.text() << ": while removing signature");
+        return EXITCODE_SIGNATURE_REMOVAL_FAILED;
+      }
+    }
+    signer.detach();
+    stack.pop(); // remove pointer to the Digital Signatures Sequence that we've just deleted.
+    sigItem = DcmSignature::findNextSignatureItem(*dataset, stack);
+  }
+  DCMSIGN_INFO(counter << " signatures found and removed from dataset.");
+  return EXITCODE_NO_ERROR;
+}
+
+
+int DcmSignatureHelper::do_remove(
+  DcmItem *dataset,
+  const char *opt_location)
+{
+  OFCondition sicond = EC_Normal;
+  DcmSignature signer;
+  OFString aString;
+  DcmStack stack;
+  unsigned long cardSQ;
+  unsigned long i;
+  DcmItem *sigItem = DcmSignature::findFirstSignatureItem(*dataset, stack);
+  while (sigItem)
+  {
+    signer.attach(sigItem);
+    cardSQ = signer.numberOfSignatures();
+    for (i=0; i<cardSQ; i++)
+    {
+      if (EC_Normal == signer.selectSignature(i))
+      {
+        if (EC_Normal == signer.getCurrentSignatureUID(aString))
+        {
+          if (aString == opt_location)
+          {
+            DCMSIGN_WARN("Signature UID=" << aString);
+            printSignatureItemPosition(stack, aString);
+            DCMSIGN_WARN("  Location                    : " << aString);
+            sicond = signer.removeSignature(i);
+            if (sicond != EC_Normal)
+            {
+              DCMSIGN_ERROR(sicond.text() << ": while removing signature");
+              return EXITCODE_SIGNATURE_REMOVAL_FAILED;
+            } else {
+              return EXITCODE_NO_ERROR;
+            }
+          }
+        }
+      }
+    }
+    signer.detach();
+    sigItem = DcmSignature::findNextSignatureItem(*dataset, stack);
+  }
+  DCMSIGN_ERROR("signature with UID '" << opt_location << "' not found.");
+  return EXITCODE_SIGNATURE_UID_NOT_FOUND;
+}
+
+int DcmSignatureHelper::do_insert_ts(DcmItem *dataset, SiTimeStampFS *timeStamp)
+{
+  // check parameters
+  if (dataset == NULL || timeStamp == NULL) return EXITCODE_CANNOT_ACCESS_TS;
+
+  // load timestamp query
+  if (timeStamp->load_ts_query_from_file().bad())
+  {
+    return EXITCODE_CANNOT_READ_TSQ_FILE;
+  }
+
+  // load timestamp response
+  if (timeStamp->load_ts_response_from_file().bad())
+  {
+    return EXITCODE_CANNOT_READ_TSR_FILE;
+  }
+
+  // load digital signature UID
+  OFString uid;
+  OFCondition result = timeStamp->getUIDFromFile(uid);
+  if (result.bad()) return EXITCODE_CANNOT_READ_UID_FILE;
+
+  // locate digital signature
+  DcmSignature signer;
+  OFString currentUID;
+  DcmStack stack;
+  unsigned long cardSQ;
+  unsigned long i;
+  OFBool found = OFFalse;
+
+  DcmItem *sigItem = DcmSignature::findFirstSignatureItem(*dataset, stack);
+  while (sigItem)
+  {
+    // attach the item in which a digital signatures sequence was found
+    signer.attach(sigItem);
+    // determine the number of signatures in this item
+    cardSQ = signer.numberOfSignatures();
+    for (i=0; i<cardSQ; i++)
+    {
+      if (signer.selectSignature(i).good() && signer.getCurrentSignatureUID(currentUID).good() && (currentUID == uid))
+      {
+        // we have found the right digital signature
+        found = OFTrue;
+        DcmItem *currentSignatureItem = signer.getSelectedSignatureItem();
+        if (currentSignatureItem == NULL)
+        {
+          return EXITCODE_CANNOT_ACCESS_SIGNATURE; // should never happen
+        }
+        else
+        {
+          // check if the timestamp response matches the query and the dataset
+          result = timeStamp->check_ts_response(*currentSignatureItem);
+          if (result.bad()) return EXITCODE_TS_CONSISTENCY_CHECK_FAILED;
+
+          // write timestamp to dataset
+          result = timeStamp->write_ts_token(*currentSignatureItem);
+          if (result.bad()) return EXITCODE_CANNOT_INSERT_TS;
+        }
+      }
+    }
+    signer.detach();
+    if (found) sigItem = NULL; else sigItem = DcmSignature::findNextSignatureItem(*dataset, stack);
+  }
+
+  if (!found)
+  {
+    DCMSIGN_ERROR("signature with UID '" << uid << "' not found.");
+    return EXITCODE_SIGNATURE_UID_NOT_FOUND;
+  }
+  return EXITCODE_NO_ERROR;
+}
+
+
+void DcmSignatureHelper::printSignatureDetails(DcmSignature& sig, DcmStack& stack, int count)
+{
+  OFString aString;
+  OFString codeValue;
+  OFString codeMeaning;
+  OFString codingSchemeDesignator;
+  Uint16 macID = 0;
+  DcmAttributeTag at(DCM_DataElementsSigned);
+  DcmTagKey tagkey;
+  DcmTag tag;
+  const char *tagName = NULL;
+
+  if (EC_Normal == sig.getCurrentSignatureUID(aString))
+    DCMSIGN_WARN("Signature #" << count << " UID=" << aString);
+  else
+    DCMSIGN_WARN("Signature #" << count << " UID=" << "(unknown)");
+  printSignatureItemPosition(stack, aString);
+  if (dcmsignLogger.isEnabledFor(OFLogger::INFO_LOG_LEVEL))
+  {
+    DCMSIGN_INFO("  Location                    : " << aString);
+    if (EC_Normal == sig.getCurrentMacID(macID))
+      DCMSIGN_INFO("  MAC ID                      : " << macID);
+    else
+      DCMSIGN_INFO("  MAC ID                      : (unknown)");
+    if (EC_Normal == sig.getCurrentMacName(aString))
+      DCMSIGN_INFO("  MAC algorithm               : " << aString);
+    else
+      DCMSIGN_INFO("  MAC algorithm               : (unknown)");
+    if (EC_Normal == sig.getCurrentMacXferSyntaxName(aString))
+      DCMSIGN_INFO("  MAC calculation xfer syntax : " << aString);
+    else
+      DCMSIGN_INFO("  MAC calculation xfer syntax : (unknown)");
+    // data elements signed
+    if (EC_Normal != sig.getCurrentDataElementsSigned(at))
+      DCMSIGN_INFO("  Data elements signed        : (unknown)");
+    else
+    {
+      DCMSIGN_INFO("  Data elements signed        :");
+      unsigned long atVM = at.getVM();
+      for (unsigned long n=0; n<atVM; n++)
+      {
+        if (EC_Normal == at.getTagVal(tagkey, n))
+        {
+          tag = tagkey;
+          tagName = tag.getTagName();
+          DCMSIGN_INFO("      " << tagkey << " " << (tagName != NULL ? tagName : ""));
+        }
+      }
+    }
+    if (EC_Normal == sig.getCurrentSignatureDateTime(aString))
+      DCMSIGN_INFO("  Signature date/time         : " << aString);
+    else
+      DCMSIGN_INFO("  Signature date/time         : (unknown)");
+
+    if (sig.getCurrentSignaturePurpose(codeValue, codeMeaning, codingSchemeDesignator).good())
+      DCMSIGN_INFO("  Signature purpose           : " << codeMeaning << " (" << codeValue << ", " << codingSchemeDesignator << ")" );
+    else
+      DCMSIGN_INFO("  Signature purpose           : (not specified)");
+
+    DCMSIGN_INFO("  Certificate of signer       : ");
+    SiCertificate *cert = sig.getCurrentCertificate();
+    if ((cert == NULL)||(cert->getKeyType()==EKT_none))
+      DCMSIGN_INFO("      none");
+    else
+    {
+      DCMSIGN_INFO("      X.509v" << cert->getX509Version());
+      cert->getCertSubjectName(aString);
+      DCMSIGN_INFO("      Subject                 : " << aString);
+      cert->getCertIssuerName(aString);
+      DCMSIGN_INFO("      Issued by               : " << aString);
+      DCMSIGN_INFO("      Serial no.              : " << cert->getCertSerialNo());
+      cert->getCertValidityNotBefore(aString);
+      DCMSIGN_INFO("      Validity                : not before " << aString);
+      cert->getCertValidityNotAfter(aString);
+      DCMSIGN_INFO("      Validity                : not after " << aString);
+      const char *ecname = NULL;
+      switch (cert->getKeyType())
+      {
+        case EKT_RSA:
+          DCMSIGN_INFO("      Public key              : RSA, " << cert->getCertKeyBits() << " bits");
+          break;
+        case EKT_DSA:
+          DCMSIGN_INFO("      Public key              : DSA, " << cert->getCertKeyBits() << " bits");
+          break;
+        case EKT_EC:
+          ecname = cert->getCertCurveName();
+          if (ecname)
+          {
+            DCMSIGN_INFO("      Public key              : EC, curve " << ecname << ", " << cert->getCertKeyBits() << " bits");
+          }
+          else
+          {
+            DCMSIGN_INFO("      Public key              : EC, " << cert->getCertKeyBits() << " bits");
+          }
+          break;
+        case EKT_DH:
+          DCMSIGN_INFO("      Public key              : DH, " << cert->getCertKeyBits() << " bits");
+          break;
+        default:
+        case EKT_none: // should never happen
+          DCMSIGN_INFO("      Public key              : unknown type");
+          break;
+      }
+    }
+  } else {
+    DCMSIGN_INFO("  Location     : " << aString);
+  }
+}
+
+
+void DcmSignatureHelper::printTimestampDetails(DcmSignature& sig, E_TimestampVerificationPolicy tsPolicy)
+{
+  SiTimeStamp *tstamp = sig.getCurrentTimestamp();
+  OFBool haveTS = (tstamp != NULL) && tstamp->have_tsinfo();
+
+  if (dcmsignLogger.isEnabledFor(OFLogger::INFO_LOG_LEVEL))
+  {
+    switch (tsPolicy)
+    {
+      case ETVP_verifyTSIfPresent:
+        if (haveTS)
+        {
+          DCMSIGN_INFO("  Certified timestamp         : CMS_TSP version " << tstamp->get_tsinfo_version());
+        }
+        else
+        {
+          DCMSIGN_INFO("  Certified timestamp         : absent");
+          return;
+        }
+        break;
+      case ETVP_ignoreTS:
+        if (haveTS)
+        {
+          DCMSIGN_INFO("  Certified timestamp         : present, but ignored according to timestamp policy");
+          return;
+        }
+        else
+        {
+          DCMSIGN_INFO("  Certified timestamp         : absent");
+          return;
+        }
+        break;
+
+      case ETVP_requireTS:
+        if (haveTS)
+        {
+          DCMSIGN_INFO("  Certified timestamp         : CMS_TSP version " << tstamp->get_tsinfo_version());
+        }
+        else
+        {
+          DCMSIGN_INFO("  Certified timestamp         : absent, but required by timestamp policy");
+          return;
+        }
+        break;
+    }
+  }
+
+  if (haveTS)
+  {
+    // Now print timestamp details
+    OFString s;
+    tstamp->get_tsinfo_policy_oid(s);
+    DCMSIGN_INFO("      Policy OID              : " << s);
+    tstamp->get_tsinfo_imprint_algorithm_name(s);
+    DCMSIGN_INFO("      Imprint MAC algorithm   : " << s);
+    tstamp->get_tsinfo_serial_number(s);
+    DCMSIGN_INFO("      Serial number           : " << s);
+    tstamp->get_tsinfo_nonce(s);
+    if (s.length() == 0) s = "none";
+    DCMSIGN_INFO("      Nonce                   : " << s);
+    tstamp->get_tsinfo_tsa_name(s);
+    if (s.length() == 0) s = "none";
+    DCMSIGN_INFO("      TSA Name                : " << s);
+    DCMSIGN_INFO("      Ordering                : " << (tstamp->get_tsinfo_ordering() ? "true" : "false" ));
+    tstamp->get_tsinfo_accuracy(s);
+    if (s.length() == 0) s = "not specified";
+    DCMSIGN_INFO("      Accuracy                : " << s);
+    tstamp->get_tsinfo_timestamp(s);
+    DCMSIGN_INFO("      Timestamp               : " << s);
+    tstamp->get_tsinfo_policy_oid(s);
+
+    // finally, print extensions (if any)
+    int numext = tstamp->get_tsinfo_numextensions();
+    if (numext == 0)
+    {
+      DCMSIGN_INFO("      Extensions              : none");
+    }
+    else
+    {
+      DCMSIGN_INFO("      Extensions              :");
+      for (int i=0; i<numext; ++i)
+      {
+        tstamp->get_tsinfo_extension(s, i);
+        DCMSIGN_INFO("        - " << s);
+      }
+    }
+  }
+}
+
+
+
+#else /* WITH_OPENSSL */
+
+int sisighlp_cc_dummy_to_keep_linker_from_moaning = 0;
+
+#endif
index 19393cf86c29758c9a3b86093bc7175899a44b85..e22ab23e3437d4ece5f0bab803a19d839a76268c 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2000-2010, OFFIS e.V.
+ *  Copyright (C) 2000-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #include "dcmtk/dcmdata/dcvrui.h"
 #include "dcmtk/dcmdata/dcvrobow.h"
 #include "dcmtk/dcmdata/dcvrus.h"
+#include "dcmtk/dcmdata/dcvrdt.h"
 #include "dcmtk/dcmdata/dcuid.h"
 #include "dcmtk/dcmdata/dcsequen.h"
 #include "dcmtk/dcmdata/dcdeftag.h"
-
+#include "dcmtk/ofstd/ofstd.h"
 #include "dcmtk/dcmsign/sialgo.h"
 #include "dcmtk/dcmsign/sicert.h"
 #include "dcmtk/dcmsign/simac.h"
@@ -50,6 +51,7 @@
 #include "dcmtk/dcmsign/sisha512.h"
 #include "dcmtk/dcmsign/sisprof.h"
 #include "dcmtk/dcmsign/sitstamp.h"
+#include "dcmtk/dcmsign/sitsfs.h"
 
 BEGIN_EXTERN_C
 #include <openssl/evp.h>
@@ -65,21 +67,21 @@ void DcmSignature::initializeLibrary()
   ERR_load_crypto_strings();
 }
 
-
-Uint16 DcmSignature::getMACIDnumber(DcmItem &item)
+OFCondition DcmSignature::getMACIDnumber(DcmItem &item, Uint16& macid)
 {
-  Uint16 macIDnumber = 0;
+  macid = 0xFFFF;
   DcmStack stack;
-  if (item.search(DCM_MACIDNumber, stack, ESM_fromHere, OFFalse).good() && (stack.top()->isLeaf()))
+  OFCondition result = item.search(DCM_MACIDNumber, stack, ESM_fromHere, OFFalse);
+  if (result.good() && (stack.top()->isLeaf()))
   {
-    ((DcmElement *)(stack.top()))->getUint16(macIDnumber);
+    result = ((DcmElement *)(stack.top()))->getUint16(macid);
   }
-  return macIDnumber;
+  return result;
 }
 
-
 void DcmSignature::currentDateTime(OFString &str)
 {
+  str = "";
   DcmDateTime::getCurrentDateTime(str, OFTrue /*seconds*/, OFTrue /*fraction*/, OFTrue /*timeZone*/);
 }
 
@@ -95,6 +97,7 @@ DcmSignature::DcmSignature()
 , selectedSignatureItem(NULL)
 , selectedMacParametersItem(NULL)
 , selectedCertificate(NULL)
+, selectedTimestamp(NULL)
 {
 }
 
@@ -111,6 +114,8 @@ void DcmSignature::deselect()
   selectedMacParametersItem = NULL;
   delete selectedCertificate;
   selectedCertificate = NULL;
+  delete selectedTimestamp;
+  selectedTimestamp = NULL;
 }
 
 
@@ -167,15 +172,19 @@ OFCondition DcmSignature::removeSignature(unsigned long i)
   DcmItem *removalItem = signatureSq->getItem(i);
   if (removalItem == NULL) return EC_IllegalCall; // should never happen
 
+  Uint16 macIDnumber = 0;
+  OFCondition result = getMACIDnumber(*removalItem, macIDnumber);
+  if (result.bad()) return result;
+
   // check mac ID number and whether it is unique
-  Uint16 macIDnumber = getMACIDnumber(*removalItem);
   OFBool macIDunique = OFTrue;
   DcmItem *tmpItem=NULL;
   unsigned long j=0;
+  Uint16 macIDnumber2 = 0;
   for (j=0; j < seqCard; ++j)
   {
     tmpItem = signatureSq->getItem(j);
-    if ((i != j) && tmpItem && (macIDnumber == getMACIDnumber(*tmpItem))) macIDunique = OFFalse;
+    if ((i != j) && tmpItem && (getMACIDnumber(*tmpItem, macIDnumber2).good()) && (macIDnumber == macIDnumber2)) macIDunique = OFFalse;
   }
 
   // delete signature item
@@ -188,7 +197,7 @@ OFCondition DcmSignature::removeSignature(unsigned long i)
     while (j < macParametersSq->card())
     {
       tmpItem = macParametersSq->getItem(j);
-      if (tmpItem && (macIDnumber == getMACIDnumber(*tmpItem))) delete macParametersSq->remove(j); else ++j;
+      if (tmpItem && (getMACIDnumber(*tmpItem, macIDnumber2).good()) && (macIDnumber == macIDnumber2)) delete macParametersSq->remove(j); else ++j;
     }
   }
 
@@ -224,6 +233,7 @@ OFCondition DcmSignature::allocateMACID(Uint16& newID)
   if (isAllocated==NULL) return EC_MemoryExhausted;
 
   OFCondition result = SI_EC_MacIDsExhausted;
+  Uint16 macID = 0;
 
   for (i=0; i < 65536; ++i) isAllocated[i]=0;
   if (signatureSq)
@@ -232,7 +242,10 @@ OFCondition DcmSignature::allocateMACID(Uint16& newID)
     for (i=0; i < sqCard; ++i)
     {
       tmpItem = signatureSq->getItem(i);
-      if (tmpItem) isAllocated[getMACIDnumber(*tmpItem)] = 1;
+      if (tmpItem && getMACIDnumber(*tmpItem, macID).good())
+      {
+        isAllocated[macID] = 1;
+      }
     }
   }
   if (macParametersSq)
@@ -241,7 +254,10 @@ OFCondition DcmSignature::allocateMACID(Uint16& newID)
     for (i=0; i < macCard; ++i)
     {
       tmpItem = macParametersSq->getItem(i);
-      if (tmpItem) isAllocated[getMACIDnumber(*tmpItem)] = 1;
+      if (tmpItem && getMACIDnumber(*tmpItem, macID).good())
+      {
+        isAllocated[macID] = 1;
+      }
     }
   }
   i = 0;
@@ -266,7 +282,8 @@ OFCondition DcmSignature::createSignature(
     SiSecurityProfile& profile,
     E_TransferSyntax xfer,
     const DcmAttributeTag *tagList,
-    SiTimeStamp *timeStamp)
+    SiTimeStamp *timeStamp,
+    SiSignaturePurpose::E_SignaturePurposeType sigPurpose)
 {
   // do some checks first
   if (currentItem == NULL) return EC_IllegalCall;
@@ -277,7 +294,26 @@ OFCondition DcmSignature::createSignature(
 
   OFCondition result = EC_Normal;
 
-  // update tag list if present
+  // print a warning if we have a weak (i.e. too short) key in the certificate
+  cert.checkForWeakKey();
+
+  // print a warning if the certificate has already expired
+  if (cert.isCertExpiredNow())
+  {
+    OFString expiry;
+    cert.getCertValidityNotAfter(expiry);
+    DCMSIGN_WARN("Certificate has expired " << expiry << ", signature will be invalid.");
+  }
+
+  // print a warning if the certificate is not yet valid
+  if (cert.isCertNotYetValidNow())
+  {
+    OFString notBefore;
+    cert.getCertValidityNotBefore(notBefore);
+    DCMSIGN_WARN("Certificate is not yet valid, validity starts " << notBefore << ", signature will be invalid.");
+  }
+
+  // create updated tag list
   DcmAttributeTag *updatedTagList = NULL;
   if (tagList)
   {
@@ -285,6 +321,12 @@ OFCondition DcmSignature::createSignature(
     if (updatedTagList == NULL) result = EC_MemoryExhausted;
     else result = profile.updateAttributeList(*currentItem, *updatedTagList);
   }
+  else
+  {
+    updatedTagList = new DcmAttributeTag(DCM_DataElementsSigned);
+    if (updatedTagList == NULL) result = EC_MemoryExhausted;
+    else result = profile.createAttributeList(*currentItem, *updatedTagList);
+  }
 
   // make sure we have a MAC parameter sequence
   if ((result.good()) && (macParametersSq == NULL))
@@ -369,6 +411,17 @@ OFCondition DcmSignature::createSignature(
         } else result = EC_MemoryExhausted;
       }
 
+      // Digital Signature Purpose Code Sequence
+      if (result.good())
+      {
+
+        // check if the signature profile requires a certain signature purpose
+        sigPurpose = SiSignaturePurpose::determineOverridePurpose(sigPurpose, profile.getOverrideSignaturePurpose());
+
+        // create digital signature purpose code sequence (unless sigPurpose is ESP_none)
+        result = SiSignaturePurpose::insertDigitalSignaturePurposeCodeSQ(*seqItem, sigPurpose);
+      }
+
       // Certificate of Signer and Certificate Type
       if (result.good())
       {
@@ -386,6 +439,8 @@ OFCondition DcmSignature::createSignature(
   if (tagListOut == NULL) result = EC_MemoryExhausted;
   unsigned long sigLength = 0;
   unsigned char *signature = NULL;
+  unsigned long digestLength = mac.getSize();
+  unsigned char *digest = new unsigned char[digestLength];
 
   if (result.good())
   {
@@ -408,17 +463,20 @@ OFCondition DcmSignature::createSignature(
     } else result = EC_MemoryExhausted;
   }
 
+  // check whether all tags from tagList are really present in the signature
+  if (result.good())
+  {
+    result = checkListOfSignedTags(tagList, tagListOut);
+  }
+
   // sign MAC
   if (result.good())
   {
-    unsigned long digestLength = mac.getSize();
-    unsigned char *digest = new unsigned char[digestLength];
     if (digest == NULL) result = EC_MemoryExhausted;
     else
     {
       result = mac.finalize(digest);
       if (result.good()) result = algorithm->sign(digest, digestLength, mac.macType(), signature, sigLength);
-      delete[] digest;
     }
   }
 
@@ -449,7 +507,16 @@ OFCondition DcmSignature::createSignature(
       {
         if (timeStamp)
         {
-          // this would be the right time to request the time stamp
+          // now is the right time to request the certified time stamp
+
+          // check if the digital signature has an odd number of bytes
+          if (algorithm->keyType() == EKT_DSA || algorithm->keyType() == EKT_EC)
+          {
+              // DSA and ECDSA signatures are encoded in DER and can have odd length. We must remove
+              // the pad byte before feeding the signature to the timestamping layer.
+              adjustASN1SequenceLength(signature, sigLength);
+          }
+
           result = timeStamp->stamp(signature, sigLength);
           if (result.good())
           {
@@ -543,6 +610,7 @@ OFCondition DcmSignature::createSignature(
   }
 
   delete[] signature;
+  delete[] digest;
   delete tagListOut;
   delete updatedTagList;
   delete algorithm;
@@ -557,15 +625,24 @@ OFCondition DcmSignature::selectSignature(unsigned long i)
 
   selectedSignatureItem = signatureSq->getItem(i);
   if (selectedSignatureItem == NULL) return EC_IllegalCall;
-  Uint16 macID = getMACIDnumber(*selectedSignatureItem);
+
+  selectedMacParametersItem = NULL;
+  Uint16 macID = 0xFFFF;
+  OFCondition result = getMACIDnumber(*selectedSignatureItem, macID);
+  if (result.bad())
+  {
+    DCMSIGN_WARN("Cannot read MAC ID number in DigitalSignaturesSequence.");
+  }
+
   if (macParametersSq)
   {
+    Uint16 macID2 = 0;
     DcmItem *tmpItem=NULL;
     unsigned long cardMac = macParametersSq->card();
     for (unsigned long j=0; j<cardMac; j++)
     {
       tmpItem = macParametersSq->getItem(j);
-      if (macID == getMACIDnumber(*tmpItem))
+      if (result.good() && getMACIDnumber(*tmpItem, macID2).good() &&  macID == macID2)
       {
         selectedMacParametersItem = tmpItem;
         break;
@@ -574,7 +651,25 @@ OFCondition DcmSignature::selectSignature(unsigned long i)
   }
   selectedCertificate = new SiCertificate();
   if (selectedCertificate == NULL) return EC_MemoryExhausted;
-  selectedCertificate->read(*selectedSignatureItem);
+  result = selectedCertificate->read(*selectedSignatureItem);
+  if (result.bad())
+  {
+    // a failure to read the certificate should not cause a failure
+    // of the "selectSignature" operation. We actually want the
+    // signature verification to fail in this case.
+    DCMSIGN_DEBUG(result.text() << " while reading certificate.");
+  }
+
+  selectedTimestamp = new SiTimeStampFS();
+  if (selectedTimestamp == NULL) return EC_MemoryExhausted;
+  result = selectedTimestamp->read(*selectedSignatureItem);
+  if (result.bad() && (result != EC_TagNotFound))
+  {
+    DCMSIGN_WARN(result.text() << " while reading timestamp.");
+    delete selectedTimestamp;
+    selectedTimestamp = NULL;
+  }
+
   return EC_Normal;
 }
 
@@ -634,7 +729,9 @@ OFCondition DcmSignature::verifyCurrent()
     {
       tagList = new DcmAttributeTag(*((DcmAttributeTag *)(stack.top())));
       if (tagList == NULL) result = EC_MemoryExhausted;
+      else if (tagList->getVM() == 0) result = SI_EC_VerificationFailed_NoDataElementsSigned; // DataElementsSigned is present but empty
     }
+    else result = SI_EC_VerificationFailed_NoDataElementsSigned; // DataElementsSigned is absent or does not have "AT" VR
   }
 
   // read Signature
@@ -651,12 +748,11 @@ OFCondition DcmSignature::verifyCurrent()
   // create MAC
   if (result.good())
   {
-    DcmAttributeTag tagListOut(DCM_DataElementsSigned);
     SiMACConstructor constructor;
     if (dumpFile) constructor.setDumpFile(dumpFile);
 
     // encode main dataset
-    result = constructor.encodeDataset(*currentItem, *mac, xfer, tagListOut, tagList);
+    result = constructor.encodeDatasetForVerification(*currentItem, *mac, xfer, tagList);
 
     // encode required attributes from the digital signatures sequence
     if (result.good()) result = constructor.encodeDigitalSignatureItem(*selectedSignatureItem, *mac, xfer);
@@ -672,11 +768,19 @@ OFCondition DcmSignature::verifyCurrent()
     if (algorithm)
     {
       OFBool verified = OFTrue;
-      Uint32 sigLength = signature->getLength();
+      unsigned long sigLength = signature->getLength();
       Uint8 *sigData = NULL;
       if ((signature->getUint8Array(sigData)).bad() || (sigData == NULL)) result = SI_EC_VerificationFailed_NoSignature;
       else
       {
+        // check if the digital signature has an odd number of bytes
+        if (selectedCertificate->getKeyType() == EKT_DSA || selectedCertificate->getKeyType() == EKT_EC)
+        {
+            // DSA and ECDSA signatures are encoded in DER and can have odd length. We must remove
+            // the pad byte before feeding the signature to the OpenSSL layer.
+            adjustASN1SequenceLength(sigData, sigLength);
+        }
+
         unsigned long digestLength = mac->getSize();
         unsigned char *digest = new unsigned char[digestLength];
         if (digest == NULL) result =  EC_MemoryExhausted;
@@ -695,6 +799,45 @@ OFCondition DcmSignature::verifyCurrent()
     } else result = SI_EC_VerificationFailed_NoCertificate;
   }
 
+  // check signature date against certificate expiry date
+  if (result.good())
+  {
+    DcmDateTime *dt = getCurrentSignatureDateTime();
+    if (dt)
+    {
+      OFDateTime odt;
+      result = dt->getOFDateTime(odt);
+      if (result.good())
+      {
+        // convert DICOM datetime string to YYYYMMDDHHMMSSZ format.
+        // Note that we ignore the timezone here, which not correct
+        // (we should adjust the datetime for the timezone)
+        OFString asn1dt;
+        char buf[40];
+        OFStandard::snprintf(buf, 40, "%04u%02u%02u%02u%02u%02uZ",
+          odt.getDate().getYear(), odt.getDate().getMonth(), odt.getDate().getDay(),
+          odt.getTime().getHour(), odt.getTime().getMinute(), odt.getTime().getIntSecond());
+        asn1dt = buf;
+        if (selectedCertificate->isCertExpiredAt(asn1dt))
+        {
+          // certificate was already expired at signature date time
+          result = SI_EC_VerificationFailed_CertExpiredAtSignature;
+        }
+        else if (selectedCertificate->isCertNotYetValidAt(asn1dt))
+        {
+          // certificate was not yet valid at signature date time,
+          // so this is probably a backdated signature
+          result = SI_EC_VerificationFailed_CertNotYetValidAtSig;
+        }
+      }
+    }
+    else
+    {
+      DCMSIGN_WARN("DigitalSignatureDateTime attribute is invalid");
+      result = SI_EC_VerificationFailed_CertExpiredAtSignature;
+    }
+  }
+
   delete signature;
   delete tagList;
   delete mac;
@@ -711,19 +854,46 @@ DcmItem *DcmSignature::findFirstSignatureItem(DcmItem& item, DcmStack& stack)
 
 DcmItem *DcmSignature::findNextSignatureItem(DcmItem& item, DcmStack& stack)
 {
-  if (item.search(DCM_DigitalSignaturesSequence, stack, ESM_afterStackTop, OFTrue).good())
+  do
   {
-    DcmObject *nextItem = stack.elem(1);
-    if (nextItem && ((nextItem->ident() == EVR_item) || (nextItem->ident() == EVR_dataset))) return (DcmItem *)nextItem;
-  }
-  return NULL;
+    if (item.search(DCM_DigitalSignaturesSequence, stack, ESM_afterStackTop, OFTrue).good())
+    {
+      // We have found a DigitalSignaturesSequence. Check if the sequence is
+      // located within the OriginalAttributesSequence. This would indicate that
+      // this is an "old" signature that was valid before some update was applied
+      // to the DICOM object. This signature thus cannot and should not be verified.
+      // We currently have no code that would "undo" the modifications by moving
+      // the content of the OriginalAttributesSequence back to its original place
+      // and then try to verify the signature. For now we only inform the user
+      // about the situation.
+      DcmObject *nextItem = NULL;
+      unsigned long card = stack.card();
+      OFBool inOriginalAttributesSequence = OFFalse;
+      for (unsigned long i=0; i<card; ++i)
+      {
+        nextItem = stack.elem(i);
+        if (nextItem && nextItem->getTag() == DCM_OriginalAttributesSequence)
+        {
+          DCMSIGN_WARN("Found Digital Signature Sequence within the Original Attributes Sequence, ignoring.");
+          inOriginalAttributesSequence = OFTrue;
+          break; // break out of for loop
+        }
+      }
+      if (inOriginalAttributesSequence) continue; // skip to next iteration of do-while loop
+
+      // we're not in the OriginalAttributesSequence. Return a pointer to the dataset
+      // or item in which the DigitalSignaturesSequence is contained.
+      nextItem = stack.elem(1);
+      if (nextItem && ((nextItem->ident() == EVR_item) || (nextItem->ident() == EVR_dataset))) return (DcmItem *)nextItem;
+    }
+    return NULL; // no signature found or invalid VR (i.e. something has gone very wrong)
+  } while (OFTrue);
 }
 
 OFCondition DcmSignature::getCurrentMacID(Uint16& macID)
 {
   if (NULL == selectedSignatureItem) return EC_IllegalCall;
-  macID = getMACIDnumber(*selectedSignatureItem);
-  return EC_Normal;
+  return getMACIDnumber(*selectedSignatureItem, macID);
 }
 
 OFCondition DcmSignature::getCurrentMacXferSyntaxName(OFString& str)
@@ -737,7 +907,7 @@ OFCondition DcmSignature::getCurrentMacXferSyntaxName(OFString& str)
   if ((selectedMacParametersItem->search(DCM_MACCalculationTransferSyntaxUID, stack, ESM_fromHere, OFFalse)).good() && (stack.top()->isLeaf()))
   {
     char *uid = NULL;
-    if ((((DcmElement *)(stack.top()))->getString(uid)).good())
+    if ((((DcmElement *)(stack.top()))->getString(uid)).good() && uid)
     {
       DcmXfer xf(uid);
       if (xf.getXfer() == EXS_Unknown) str=uid; else
@@ -750,6 +920,27 @@ OFCondition DcmSignature::getCurrentMacXferSyntaxName(OFString& str)
   return result;
 }
 
+
+OFCondition DcmSignature::getCurrentSignaturePurpose(OFString& codeValue, OFString& codeMeaning, OFString& codingSchemeDesignator)
+{
+  codeValue.clear();
+  codeMeaning.clear();
+  codingSchemeDesignator.clear();
+
+  if ((NULL == selectedSignatureItem)||(NULL == selectedMacParametersItem)) return EC_IllegalCall;
+
+  DcmItem *item = NULL;
+  OFCondition result = selectedSignatureItem->findAndGetSequenceItem(DCM_DigitalSignaturePurposeCodeSequence, item, 0);
+  if (result.good())
+  {
+    result = item->findAndGetOFString(DCM_CodeValue, codeValue);
+    if (result.good()) result = item->findAndGetOFString(DCM_CodeValue, codeValue);
+    if (result.good()) result = item->findAndGetOFString(DCM_CodeMeaning, codeMeaning);
+    if (result.good()) result = item->findAndGetOFString(DCM_CodingSchemeDesignator, codingSchemeDesignator);
+  }
+  return result;
+}
+
 OFCondition DcmSignature::getCurrentMacName(OFString& str)
 {
   str.clear();
@@ -780,6 +971,19 @@ OFCondition DcmSignature::getCurrentSignatureUID(OFString& str)
   return result;
 }
 
+DcmDateTime *DcmSignature::getCurrentSignatureDateTime()
+{
+  DcmStack stack;
+  if (selectedSignatureItem && (selectedSignatureItem->search(DCM_DigitalSignatureDateTime, stack, ESM_fromHere, OFFalse)).good() && (stack.top()->isLeaf()))
+  {
+     if (stack.top()->ident() == EVR_DT)
+     {
+         return OFreinterpret_cast(DcmDateTime *, stack.top());
+     }
+  }
+  return NULL;
+}
+
 OFCondition DcmSignature::getCurrentSignatureDateTime(OFString& str)
 {
   str.clear();
@@ -800,6 +1004,11 @@ SiCertificate *DcmSignature::getCurrentCertificate()
   return selectedCertificate;
 }
 
+SiTimeStamp *DcmSignature::getCurrentTimestamp()
+{
+  return selectedTimestamp;
+}
+
 OFCondition DcmSignature::getCurrentDataElementsSigned(DcmAttributeTag& desig)
 {
   desig.clear();
@@ -816,6 +1025,140 @@ OFCondition DcmSignature::getCurrentDataElementsSigned(DcmAttributeTag& desig)
   return result;
 }
 
+DcmItem *DcmSignature::getSelectedSignatureItem()
+{
+  return selectedSignatureItem;
+}
+
+void DcmSignature::adjustASN1SequenceLength(const unsigned char *buf, unsigned long& buflen)
+{
+   // ASN.1 sequence objects encoded in DER can have odd length. Remove the pad byte, if any.
+   if (((buflen > 2) && buf && (buf[0] == 0x30) && (buf[1] < 128) && (buf[1]+3U == buflen)) || // one-byte length encoding
+       ((buflen > 4) && buf && (buf[0] == 0x30) && (buf[1] == 0x82) && ((256UL * buf[2]) + buf[3] + 5U == buflen))) // two-byte length encoding
+   {
+       // The first byte of the signature is 0x30 (DER encoding for SEQUENCE)
+       // and length field is one byte shorter than our buffer size.
+       // Adjust buflen to remove the pad byte.
+       --buflen;
+   }
+}
+
+
+OFCondition DcmSignature::verifySignatureProfile(SiSecurityProfile &sprof)
+{
+  if (NULL == currentItem) return EC_IllegalCall;
+  if (selectedMacParametersItem == NULL) return SI_EC_VerificationFailed_NoMAC;
+  if ((selectedCertificate == NULL)||(selectedCertificate->getKeyType() == EKT_none)) return SI_EC_VerificationFailed_NoCertificate;
+
+  E_TransferSyntax xfer = EXS_Unknown;
+  DcmStack stack;
+
+  // check if the profile only applies to main dataset level
+  if ((currentItem->ident() != EVR_dataset) && sprof.mainDatasetRequired())
+    return SI_EC_DatasetDoesNotMatchProfile;
+
+  // let the signature profile handler inspect the dataset first
+  OFCondition result = sprof.inspectSignatureDataset(*currentItem);
+
+  // check MAC Calculation Transfer Syntax UID
+  if (result.good())
+  {
+    if ((selectedMacParametersItem->search(DCM_MACCalculationTransferSyntaxUID, stack, ESM_fromHere, OFFalse)).good() && (stack.top()->isLeaf()))
+    {
+      char *uid = NULL;
+      if ((((DcmElement *)(stack.top()))->getString(uid)).good())
+      {
+        DcmXfer xf(uid);
+        xfer = xf.getXfer();
+        if ((xfer == EXS_Unknown) || (! sprof.isAllowableTransferSyntax(xfer))) result = SI_EC_TransferSyntaxDoesNotMatchProfile;
+      } else result = SI_EC_VerificationFailed_NoMAC;
+    } else result = SI_EC_VerificationFailed_NoMAC;
+  }
+
+  // check signature algorithm type
+  if (result.good())
+  {
+    if (! sprof.isAllowableAlgorithmType(selectedCertificate->getKeyType())) result = SI_EC_AlgorithmDoesNotMatchProfile;
+  }
+
+  // check MAC Algorithm
+  if (result.good())
+  {
+    E_MACType mac = EMT_RIPEMD160;
+    stack.clear();
+    if ((selectedMacParametersItem->search(DCM_MACAlgorithm, stack, ESM_fromHere, OFFalse)).good() && (stack.top()->isLeaf()))
+    {
+      OFString macidentifier;
+      if ((((DcmElement *)(stack.top()))->getOFString(macidentifier, 0)).good())
+      {
+        if (macidentifier == SI_DEFTERMS_RIPEMD160) mac = EMT_RIPEMD160;
+        else if (macidentifier == SI_DEFTERMS_SHA1) mac = EMT_SHA1;
+        else if (macidentifier == SI_DEFTERMS_MD5)  mac = EMT_MD5;
+        else if (macidentifier == SI_DEFTERMS_SHA256) mac = EMT_SHA256;
+        else if (macidentifier == SI_DEFTERMS_SHA384) mac = EMT_SHA384;
+        else if (macidentifier == SI_DEFTERMS_SHA512) mac = EMT_SHA512;
+        else result = SI_EC_VerificationFailed_UnsupportedMACAlgorithm;
+        if (result.good() && (! sprof.isAllowableMACType(mac))) result = SI_EC_MacDoesNotMatchProfile;
+      } else result = SI_EC_VerificationFailed_NoMAC;
+    } else result = SI_EC_VerificationFailed_NoMAC;
+  }
+
+  // check list of Data Elements Signed
+  if (result.good())
+  {
+    stack.clear();
+    if ((selectedMacParametersItem->search(DCM_DataElementsSigned, stack, ESM_fromHere, OFFalse)).good() && (stack.top()->ident() == EVR_AT))
+    {
+      DcmAttributeTag *tagList = new DcmAttributeTag(*((DcmAttributeTag *)(stack.top())));
+      if (tagList == NULL) result = EC_MemoryExhausted;
+      else
+      {
+        if (! sprof.checkAttributeList(*currentItem, *tagList)) result = SI_EC_DataElementsSignedDoesNotMatchProfile;
+      }
+      delete tagList;
+    }
+    else result = SI_EC_VerificationFailed_NoDataElementsSigned; // DataElementsSigned is absent or does not have "AT" VR
+  }
+
+  return result;
+}
+
+OFCondition DcmSignature::checkListOfSignedTags(const DcmAttributeTag *tagList, const DcmAttributeTag *tagListOut)
+{
+  if (tagListOut == NULL) return EC_IllegalCall;
+
+  OFCondition result = EC_Normal;
+  if (tagList)
+  {
+    DcmAttributeTag tagListNonConst(*tagList); // we need a non-const copy of tagList
+    DcmTagKey key;
+    unsigned long vm = tagListNonConst.getVM();
+    for (unsigned long i=0; i < vm; i++)
+    {
+      if ((tagListNonConst.getTagVal(key, i)).good() && (! inTagList(key, *tagListOut)))
+      {
+        result = EC_TagNotFound;
+        DCMSIGN_ERROR("attribute " << key << " should be signed but is not present in the dataset.");
+      }
+    }
+  }
+  return result;
+}
+
+OFBool DcmSignature::inTagList(const DcmTagKey &tag, const DcmAttributeTag& tagList)
+{
+  DcmTagKey key;
+  DcmAttributeTag tagListNonConst(tagList); // we need a non-const copy of tagList
+  unsigned long vm = tagListNonConst.getVM();
+  for (unsigned long i=0; i < vm; i++)
+  {
+    if ((tagListNonConst.getTagVal(key, i)).good() && (key == tag)) return OFTrue;
+  }
+  return OFFalse;
+}
+
+
+
 #else /* WITH_OPENSSL */
 
 #include "dcmtk/dcmsign/sidefine.h"
index e5ec78f17c621af3e24f20250da85f46b762c219..16100b3afc64babbbf27642a7fad50fbe9899040 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2010, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 
 #include "dcmtk/dcmsign/siautopr.h"
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmdata/dcitem.h"
+#include "dcmtk/dcmsign/sitypes.h"
 
-OFBool SiAuthorizationProfile::attributeRequired(const DcmTagKey& key) const
+SiAuthorizationProfile::SiAuthorizationProfile()
+: containsRawData_(OFFalse)
 {
-  /* SOP Class and Instance UIDs */
+}
+
+OFBool SiAuthorizationProfile::attributeRequiredIfPresent(const DcmTagKey& key) const
+{
+  // The Authorization RSA Digital Signature Profile requires that any
+  // attributes whose Values are verifiable by the technician or physician
+  // (e.g., their values are displayed to the technician or physician) must
+  // be included in the signature. This must be handled manually.
+
+  // the SOP Class and Instance UIDs
   if (key == DCM_SOPClassUID) return OFTrue;
   if (key == DCM_SOPInstanceUID) return OFTrue;
 
-  /* Study and Series Instance UIDs */
+  // the Study and Series Instance UIDs
   if (key == DCM_StudyInstanceUID) return OFTrue;
   if (key == DCM_SeriesInstanceUID) return OFTrue;
-  
-  /* Any overlay data present */
-  if ((key.getGroup() >= 0x6000) && (key.getGroup() < 0x6020) && ((key.getGroup() & 0x0001) == 0)) return OFTrue;
-  
-  /* Any image data present - we assume this means the Image Pixel Module and not just PixelData */
-  if (key.getGroup() == 0x0028) 
+
+  // any attributes of the Overlay Plane Module that are present
+  if (key == DCM_OverlayRows) return OFTrue;
+  if (key == DCM_OverlayColumns) return OFTrue;
+  if (key == DCM_OverlayType) return OFTrue;
+  if (key == DCM_OverlayOrigin) return OFTrue;
+  if (key == DCM_OverlayBitsAllocated) return OFTrue;
+  if (key == DCM_OverlayBitPosition) return OFTrue;
+  if (key == DCM_OverlayData) return OFTrue;
+  if (key == DCM_OverlayDescription) return OFTrue;
+  if (key == DCM_OverlaySubtype) return OFTrue;
+  if (key == DCM_OverlayLabel) return OFTrue;
+  if (key == DCM_ROIArea) return OFTrue;
+  if (key == DCM_ROIMean) return OFTrue;
+  if (key == DCM_ROIStandardDeviation) return OFTrue;
+
+  // any attributes of the Curve Module that are present
+  if ((key.getGroup() >= 0x5000) && (key.getGroup() < 0x5020) && ((key.getGroup() & 1) == 0))
   {
-    Uint16 elem = key.getElement();
-    if (elem == 0x0002) return OFTrue; // DCM_SamplesPerPixel
-    if (elem == 0x0004) return OFTrue; // DCM_PhotometricInterpretation
-    if (elem == 0x0006) return OFTrue; // DCM_PlanarConfiguration                   
-    if (elem == 0x0010) return OFTrue; // DCM_Rows
-    if (elem == 0x0011) return OFTrue; // DCM_Columns
-    if (elem == 0x0034) return OFTrue; // DCM_PixelAspectRatio                      
-    if (elem == 0x0100) return OFTrue; // DCM_BitsAllocated
-    if (elem == 0x0101) return OFTrue; // DCM_BitsStored                            
-    if (elem == 0x0102) return OFTrue; // DCM_HighBit                               
-    if (elem == 0x0103) return OFTrue; // DCM_PixelRepresentation                   
-    if (elem == 0x0106) return OFTrue; // DCM_SmallestImagePixelValue               
-    if (elem == 0x0107) return OFTrue; // DCM_LargestImagePixelValue                
-    if (elem == 0x1101) return OFTrue; // DCM_RedPaletteColorLookupTableDescriptor  
-    if (elem == 0x1102) return OFTrue; // DCM_GreenPaletteColorLookupTableDescriptor
-    if (elem == 0x1103) return OFTrue; // DCM_BluePaletteColorLookupTableDescriptor 
-    if (elem == 0x1201) return OFTrue; // DCM_RedPaletteColorLookupTableData        
-    if (elem == 0x1202) return OFTrue; // DCM_GreenPaletteColorLookupTableData      
-    if (elem == 0x1203) return OFTrue; // DCM_BluePaletteColorLookupTableData       
+    switch (key.getElement())
+    {
+      case 0x0005: // CurveDimensions (retired)
+      case 0x0010: // NumberOfPoints (retired)
+      case 0x0103: // DataValueRepresentation (retired)
+      case 0x3000: // CurveData (retired)
+      case 0x0022: // CurveDescription (retired)
+      case 0x0030: // AxisUnits (retired)
+      case 0x0040: // AxisLabels (retired)
+      case 0x0104: // MinimumCoordinateValue (retired)
+      case 0x0105: // MaximumCoordinateValue (retired)
+      case 0x0106: // CurveRange (retired)
+      case 0x0110: // CurveDataDescriptor (retired)
+      case 0x0112: // CoordinateStartValue (retired)
+      case 0x0114: // CoordinateStepValue (retired)
+      case 0x2500: // CurveLabel (retired)
+      case 0x2600: // ReferencedOverlaySequence (retired)
+        return OFTrue;
+        break;
+      default:
+        /* nothing */
+        break;
+    }
   }
+
+  // any attributes of the Graphic Annotation Module that are present
+  if (key == DCM_GraphicAnnotationSequence) return OFTrue;
+
+  // any attributes of the General Image Module that are present
+  if (key == DCM_InstanceNumber) return OFTrue;
+  if (key == DCM_PatientOrientation) return OFTrue;
+  if (key == DCM_ContentDate) return OFTrue;
+  if (key == DCM_ContentTime) return OFTrue;
+  if (key == DCM_ImageType) return OFTrue;
+  if (key == DCM_AcquisitionNumber) return OFTrue;
+  if (key == DCM_AcquisitionDate) return OFTrue;
+  if (key == DCM_AcquisitionTime) return OFTrue;
+  if (key == DCM_AcquisitionDateTime) return OFTrue;
+  if (key == DCM_ImagesInAcquisition) return OFTrue;
+  if (key == DCM_ImageComments) return OFTrue;
+  if (key == DCM_QualityControlImage) return OFTrue;
+  if (key == DCM_BurnedInAnnotation) return OFTrue;
+  if (key == DCM_RecognizableVisualFeatures) return OFTrue;
+  if (key == DCM_LossyImageCompression) return OFTrue;
+  if (key == DCM_LossyImageCompressionRatio) return OFTrue;
+  if (key == DCM_LossyImageCompressionMethod) return OFTrue;
+  if (key == DCM_IconImageSequence) return OFTrue;
+  if (key == DCM_PresentationLUTShape) return OFTrue;
+  if (key == DCM_IrradiationEventUID) return OFTrue;
+  if (key == DCM_RealWorldValueMappingSequence) return OFTrue;
+  if (key == DCM_ImageLaterality) return OFTrue;
+  if (key == DCM_AnatomicRegionSequence) return OFTrue;
+  if (key == DCM_PrimaryAnatomicStructureSequence) return OFTrue;
+
+  // any attributes of the Image Pixel Module that are present
+  if (key == DCM_SamplesPerPixel) return OFTrue;
+  if (key == DCM_PhotometricInterpretation) return OFTrue;
+  if (key == DCM_Rows) return OFTrue;
+  if (key == DCM_Columns) return OFTrue;
+  if (key == DCM_BitsAllocated) return OFTrue;
+  if (key == DCM_BitsStored) return OFTrue;
+  if (key == DCM_HighBit) return OFTrue;
+  if (key == DCM_PixelRepresentation) return OFTrue;
+  if (key == DCM_PlanarConfiguration) return OFTrue;
+  if (key == DCM_PixelAspectRatio) return OFTrue;
+  if (key == DCM_SmallestImagePixelValue) return OFTrue;
+  if (key == DCM_LargestImagePixelValue) return OFTrue;
+  if (key == DCM_RedPaletteColorLookupTableDescriptor) return OFTrue;
+  if (key == DCM_GreenPaletteColorLookupTableDescriptor) return OFTrue;
+  if (key == DCM_BluePaletteColorLookupTableDescriptor) return OFTrue;
+  if (key == DCM_RedPaletteColorLookupTableData) return OFTrue;
+  if (key == DCM_GreenPaletteColorLookupTableData) return OFTrue;
+  if (key == DCM_BluePaletteColorLookupTableData) return OFTrue;
+  if (key == DCM_ICCProfile) return OFTrue;
+  if (key == DCM_ColorSpace) return OFTrue;
   if (key == DCM_PixelData) return OFTrue;
+  if (key == DCM_PixelDataProviderURL) return OFTrue;
+  if (key == DCM_PixelPaddingRangeLimit) return OFTrue;
+  if (key == DCM_ExtendedOffsetTable) return OFTrue;
+  if (key == DCM_ExtendedOffsetTableLengths) return OFTrue;
+
+  // any attributes of the SR Document General Module that are present
+  // if (key == DCM_InstanceNumber) return OFTrue; // also in General Image Module
+  if (key == DCM_PreliminaryFlag) return OFTrue;
+  if (key == DCM_CompletionFlag) return OFTrue;
+  if (key == DCM_CompletionFlagDescription) return OFTrue;
+  if (key == DCM_VerificationFlag) return OFTrue;
+  // if (key == DCM_ContentDate) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentTime) return OFTrue; // also in General Image Module
+  if (key == DCM_VerifyingObserverSequence) return OFTrue;
+  if (key == DCM_AuthorObserverSequence) return OFTrue;
+  if (key == DCM_ParticipantSequence) return OFTrue;
+  if (key == DCM_CustodialOrganizationSequence) return OFTrue;
+  if (key == DCM_PredecessorDocumentsSequence) return OFTrue;
+  if (key == DCM_IdenticalDocumentsSequence) return OFTrue;
+  if (key == DCM_ReferencedRequestSequence) return OFTrue;
+  if (key == DCM_PerformedProcedureCodeSequence) return OFTrue;
+  if (key == DCM_CurrentRequestedProcedureEvidenceSequence) return OFTrue;
+  if (key == DCM_PertinentOtherEvidenceSequence) return OFTrue;
+  if (key == DCM_ReferencedInstanceSequence) return OFTrue;
+
+  // any attributes of the SR Document Content Module that are present
+  if (key == DCM_ValueType) return OFTrue;
+  if (key == DCM_ConceptNameCodeSequence) return OFTrue;
+  if (key == DCM_ContinuityOfContent) return OFTrue;
+  if (key == DCM_ContentTemplateSequence) return OFTrue;
+  if (key == DCM_ObservationDateTime) return OFTrue;
+  if (key == DCM_ObservationUID) return OFTrue;
+  if (key == DCM_ContentSequence) return OFTrue;
+
+  // any attributes of the Waveform Module that are present
+  if (key == DCM_WaveformSequence) return OFTrue;
+  if (key == DCM_WaveformDataDisplayScale) return OFTrue;
+  if (key == DCM_WaveformDisplayBackgroundCIELabValue) return OFTrue;
+  if (key == DCM_WaveformPresentationGroupSequence) return OFTrue;
+
+  // any attributes of the Waveform Annotation Module that are present
+  if (key == DCM_WaveformAnnotationSequence) return OFTrue;
+
+  // any attributes of the Multi-frame Functional Groups module that are present
+  if (key == DCM_SharedFunctionalGroupsSequence) return OFTrue;
+  if (key == DCM_PerFrameFunctionalGroupsSequence) return OFTrue;
+  // if (key == DCM_InstanceNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentDate) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentTime) return OFTrue; // also in General Image Module
+  if (key == DCM_NumberOfFrames) return OFTrue;
+  if (key == DCM_StereoPairsPresent) return OFTrue;
+  if (key == DCM_ConcatenationFrameOffsetNumber) return OFTrue;
+  if (key == DCM_RepresentativeFrameNumber) return OFTrue;
+  if (key == DCM_ConcatenationUID) return OFTrue;
+  if (key == DCM_SOPInstanceUIDOfConcatenationSource) return OFTrue;
+  if (key == DCM_InConcatenationNumber) return OFTrue;
+  if (key == DCM_InConcatenationTotalNumber) return OFTrue;
+
+  // any attributes of the Enhanced MR Image Module that are present
+  // if (key == DCM_AcquisitionNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDateTime) return OFTrue; // also in General Image Module
+  if (key == DCM_AcquisitionDuration) return OFTrue;
+  if (key == DCM_ReferencedRawDataSequence) return OFTrue;
+  if (key == DCM_ReferencedWaveformSequence) return OFTrue;
+  if (key == DCM_ReferencedImageEvidenceSequence) return OFTrue;
+  if (key == DCM_SourceImageEvidenceSequence) return OFTrue;
+  if (key == DCM_ReferencedPresentationStateSequence) return OFTrue;
+  if (key == DCM_ContentQualification) return OFTrue;
+  if (key == DCM_ResonantNucleus) return OFTrue;
+  if (key == DCM_KSpaceFiltering) return OFTrue;
+  if (key == DCM_MagneticFieldStrength) return OFTrue;
+  if (key == DCM_ApplicableSafetyStandardAgency) return OFTrue;
+  if (key == DCM_ApplicableSafetyStandardDescription) return OFTrue;
+  // if (key == DCM_ImageComments) return OFTrue; // also in General Image Module
+  if (key == DCM_IsocenterPosition) return OFTrue;
+  if (key == DCM_B1rms) return OFTrue;
+  // if (key == DCM_ImageType) return OFTrue; // also in General Image Module
+  if (key == DCM_PixelPresentation) return OFTrue;
+  if (key == DCM_VolumetricProperties) return OFTrue;
+  if (key == DCM_VolumeBasedCalculationTechnique) return OFTrue;
+  if (key == DCM_ComplexImageComponent) return OFTrue;
+  if (key == DCM_AcquisitionContrast) return OFTrue;
+  if (key == DCM_FunctionalSettlingPhaseFramesPresent) return OFTrue;
+  // if (key == DCM_SamplesPerPixel) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PhotometricInterpretation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsAllocated) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsStored) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_HighBit) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PixelRepresentation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PlanarConfiguration) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BurnedInAnnotation) return OFTrue; // also in General Image Module
+  // if (key == DCM_RecognizableVisualFeatures) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompression) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionRatio) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionMethod) return OFTrue; // also in General Image Module
+  // if (key == DCM_PresentationLUTShape) return OFTrue; // also in General Image Module
+  // if (key == DCM_IconImageSequence) return OFTrue; // also in General Image Module
+  if (key == DCM_ViewCodeSequence) return OFTrue;
+  if (key == DCM_SliceProgressionDirection) return OFTrue;
+
+  // any attributes of the MR Spectroscopy modules that are present
+  // if (key == DCM_AcquisitionNumber) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_AcquisitionDateTime) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_AcquisitionDuration) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedRawDataSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedWaveformSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_SourceImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedPresentationStateSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ContentQualification) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ResonantNucleus) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_k-SpaceFiltering) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_MagneticFieldStrength) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ApplicableSafetyStandardAgency) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ApplicableSafetyStandardDescription) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ImageComments) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_IsocenterPosition) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_B1rms) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ImageType) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_VolumetricProperties) return OFTrue; // also in Enhanced MR Image Module
+  // if (key == DCM_VolumeBasedCalculationTechnique) return OFTrue; // also in Enhanced MR Image Module
+  // if (key == DCM_ComplexImageComponent) return OFTrue; // also in Enhanced MR Image Module
+  // if (key == DCM_AcquisitionContrast) return OFTrue; // also in Enhanced MR Image Module
+  if (key == DCM_TransmitterFrequency) return OFTrue;
+  if (key == DCM_SpectralWidth) return OFTrue;
+  if (key == DCM_ChemicalShiftReference) return OFTrue;
+  if (key == DCM_VolumeLocalizationTechnique) return OFTrue;
+  if (key == DCM_VolumeLocalizationSequence) return OFTrue;
+  if (key == DCM_Decoupling) return OFTrue;
+  if (key == DCM_DecoupledNucleus) return OFTrue;
+  if (key == DCM_DecouplingFrequency) return OFTrue;
+  if (key == DCM_DecouplingMethod) return OFTrue;
+  if (key == DCM_DecouplingChemicalShiftReference) return OFTrue;
+  if (key == DCM_TimeDomainFiltering) return OFTrue;
+  if (key == DCM_NumberOfZeroFills) return OFTrue;
+  if (key == DCM_BaselineCorrection) return OFTrue;
+  if (key == DCM_FrequencyCorrection) return OFTrue;
+  if (key == DCM_FirstOrderPhaseCorrection) return OFTrue;
+  if (key == DCM_WaterReferencedPhaseCorrection) return OFTrue;
+  if (key == DCM_WaterReferenceAcquisition) return OFTrue;
+  // if (key == DCM_ReferencedInstanceSequence) return OFTrue; // also in SR Document General Module
+
+  // any attributes of the Raw Data module that are present
+  // if (key == DCM_InstanceNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentDate) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDateTime) return OFTrue; // also in General Image Module
+  if (key == DCM_ContentLabel) return OFTrue;
+  if (key == DCM_ContentDescription) return OFTrue;
+  // if (key == DCM_ConceptNameCodeSequence) return OFTrue; // also in SR Document Content Module
+  // if (key == DCM_ImageLaterality) return OFTrue; // also in General Image Module
+  if (key == DCM_CreatorVersionUID) return OFTrue;
+  // if (key == DCM_ReferencedInstanceSequence) return OFTrue; // also in SR Document General Module
+
+  // if the Raw Data Module is present, we need to include all private tags into
+  // signature because the raw data as such is stored in private attributes.
+  if (((key.getGroup() & 1) == 1) && containsRawData_) return OFTrue;
+
+  // any attributes of the Enhanced CT Image module that are present
+  // if (key == DCM_ImageType) return OFTrue; // also in General Image Module
+  if (key == DCM_MultienergyCTAcquisition) return OFTrue;
+  // if (key == DCM_AcquisitionNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDateTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDuration) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedRawDataSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedWaveformSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_SourceImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedPresentationStateSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_SamplesPerPixel) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PhotometricInterpretation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsAllocated) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsStored) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_HighBit) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_ContentQualification) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ImageComments) return OFTrue; // also in General Image Module
+  // if (key == DCM_BurnedInAnnotation) return OFTrue; // also in General Image Module
+  // if (key == DCM_RecognizableVisualFeatures) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompression) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionRatio) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionMethod) return OFTrue; // also in General Image Module
+  // if (key == DCM_PresentationLUTShape) return OFTrue; // also in General Image Module
+  // if (key == DCM_IconImageSequence) return OFTrue; // also in General Image Module
+  // if (key == DCM_IsocenterPosition) return OFTrue;  // also in Enhanced MR Image Module
+
+  // any attributes of the Enhanced XA/XRF Image module that are present
+  // if (key == DCM_ImageType) return OFTrue; // also in General Image Module
+  if (key == DCM_PlanesInAcquisition) return OFTrue;
+  if (key == DCM_PlaneIdentification) return OFTrue;
+  // if (key == DCM_AcquisitionNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDateTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_BitsAllocated) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsStored) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_HighBit) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_SamplesPerPixel) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PixelRepresentation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PhotometricInterpretation) return OFTrue; // also in Image Pixel Module
+  if (key == DCM_AcquisitionProtocolName) return OFTrue;
+  if (key == DCM_AcquisitionProtocolDescription) return OFTrue;
+  if (key == DCM_ScanOptions) return OFTrue;
+  // if (key == DCM_ContentQualification) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_PatientOrientationCodeSequence) return OFTrue; // also in General Image Module
+  if (key == DCM_PatientGantryRelationshipCodeSequence) return OFTrue;
+  if (key == DCM_ExaminedBodyThickness) return OFTrue;
+  // if (key == DCM_BurnedInAnnotation) return OFTrue; // also in General Image Module
+  // if (key == DCM_RecognizableVisualFeatures) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompression) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionRatio) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionMethod) return OFTrue; // also in General Image Module
+  if (key == DCM_ReferencedOtherPlaneSequence) return OFTrue;
+  // if (key == DCM_ReferencedImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_SourceImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedInstanceSequence) return OFTrue; // also in SR Document General Module
+  // if (key == DCM_ImageComments) return OFTrue; // also in General Image Module
+  // if (key == DCM_QualityControlImage) return OFTrue; // also in General Image Module
+  // if (key == DCM_IconImageSequence) return OFTrue; // also in General Image Module
+  // if (key == DCM_PresentationLUTShape) return OFTrue; // also in General Image Module
+
+  // any attributes of the Segmentation Image module that are present
+  // if (key == DCM_ImageType) return OFTrue; // also in General Image Module
+  if (key == DCM_ImageOrientationSlide) return OFTrue;
+  // if (key == DCM_SamplesPerPixel) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PhotometricInterpretation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PixelRepresentation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsAllocated) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsStored) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_HighBit) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_LossyImageCompression) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionRatio) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionMethod) return OFTrue; // also in General Image Module
+  if (key == DCM_SegmentationType) return OFTrue;
+  if (key == DCM_SegmentationFractionalType) return OFTrue;
+  if (key == DCM_MaximumFractionalValue) return OFTrue;
+  if (key == DCM_SegmentsOverlap) return OFTrue;
+  if (key == DCM_SegmentSequence) return OFTrue;
+
+  // any attributes of the Encapsulated Document module that are present
+  // if (key == DCM_InstanceNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentDate) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDateTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_ImageLaterality) return OFTrue; // also in General Image Module
+  // if (key == DCM_BurnedInAnnotation) return OFTrue; // also in General Image Module
+  // if (key == DCM_RecognizableVisualFeatures) return OFTrue; // also in General Image Module
+  if (key == DCM_SourceInstanceSequence) return OFTrue;
+  if (key == DCM_DocumentTitle) return OFTrue;
+  // if (key == DCM_ConceptNameCodeSequence) return OFTrue; // also in SR Document Content Module
+  if (key == DCM_DocumentClassCodeSequence) return OFTrue;
+  // if (key == DCM_VerificationFlag) return OFTrue; // also in SR Document General Module
+  if (key == DCM_HL7InstanceIdentifier) return OFTrue;
+  // if (key == DCM_PredecessorDocumentsSequence) return OFTrue; // also in SR Document General Module
+  // if (key == DCM_IdenticalDocumentsSequence) return OFTrue; // also in SR Document General Module
+  if (key == DCM_MIMETypeOfEncapsulatedDocument) return OFTrue;
+  if (key == DCM_ListOfMIMETypes) return OFTrue;
+  if (key == DCM_EncapsulatedDocument) return OFTrue;
+  if (key == DCM_EncapsulatedDocumentLength) return OFTrue;
+  // if (key == DCM_ValueType) return OFTrue; // also in SR Document Content Module
+  // if (key == DCM_ContentSequence) return OFTrue; // also in SR Document Content Module
+  // if (key == DCM_ContinuityOfContent) return OFTrue; // also in SR Document Content Module
+  // if (key == DCM_ContentTemplateSequence) return OFTrue; // also in SR Document Content Module
+
+  // any attributes of the X-Ray 3D Image module that are present
+  // if (key == DCM_ImageType) return OFTrue; // also in General Image Module
+  // if (key == DCM_BitsAllocated) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsStored) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_HighBit) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_SamplesPerPixel) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PhotometricInterpretation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_ContentQualification) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_BurnedInAnnotation) return OFTrue; // also in General Image Module
+  // if (key == DCM_RecognizableVisualFeatures) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompression) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionRatio) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionMethod) return OFTrue; // also in General Image Module
+  // if (key == DCM_ReferencedImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ImageComments) return OFTrue; // also in General Image Module
+  // if (key == DCM_QualityControlImage) return OFTrue; // also in General Image Module
+  // if (key == DCM_IconImageSequence) return OFTrue; // also in General Image Module
+  // if (key == DCM_PresentationLUTShape) return OFTrue; // also in General Image Module
+  if (key == DCM_SourceIrradiationEventSequence) return OFTrue;
+
+  // any attributes of the Enhanced PET Image module that are present
+  // if (key == DCM_ImageType) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDateTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDuration) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedRawDataSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedWaveformSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_SourceImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_SamplesPerPixel) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PhotometricInterpretation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsAllocated) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsStored) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_HighBit) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_ContentQualification) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ImageComments) return OFTrue; // also in General Image Module
+  // if (key == DCM_BurnedInAnnotation) return OFTrue; // also in General Image Module
+  // if (key == DCM_RecognizableVisualFeatures) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompression) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionRatio) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionMethod) return OFTrue; // also in General Image Module
+  // if (key == DCM_PresentationLUTShape) return OFTrue; // also in General Image Module
+  // if (key == DCM_IconImageSequence) return OFTrue; // also in General Image Module
+
+  // any attributes of the Enhanced US Image module that are present
+  // if (key == DCM_ImageType) return OFTrue; // also in General Image Module
+  // if (key == DCM_SamplesPerPixel) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PhotometricInterpretation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsAllocated) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsStored) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_HighBit) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PixelRepresentation) return OFTrue; // also in Image Pixel Module
+  if (key == DCM_DimensionOrganizationType) return OFTrue;
+  // if (key == DCM_AcquisitionDateTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDuration) return OFTrue;  // also in Enhanced MR Image Module
+  if (key == DCM_PositionMeasuringDeviceUsed) return OFTrue;
+  // if (key == DCM_LossyImageCompression) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionRatio) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionMethod) return OFTrue; // also in General Image Module
+  // if (key == DCM_PresentationLUTShape) return OFTrue; // also in General Image Module
+  if (key == DCM_RescaleIntercept) return OFTrue;
+  if (key == DCM_RescaleSlope) return OFTrue;
+  if (key == DCM_SourceImageSequence) return OFTrue;
+  if (key == DCM_ReferencedImageSequence) return OFTrue;
+  // if (key == DCM_ReferencedRawDataSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedInstanceSequence) return OFTrue; // also in SR Document General Module
+  if (key == DCM_NumberOfStages) return OFTrue;
+  if (key == DCM_StageNumber) return OFTrue;
+  if (key == DCM_StageCodeSequence) return OFTrue;
+  if (key == DCM_EventTimerSequence) return OFTrue;
+  // if (key == DCM_BurnedInAnnotation) return OFTrue; // also in General Image Module
+  // if (key == DCM_RecognizableVisualFeatures) return OFTrue; // also in General Image Module
+  // if (key == DCM_IconImageSequence) return OFTrue; // also in General Image Module
+  if (key == DCM_TransducerData) return OFTrue;
+  if (key == DCM_TransducerGeometryCodeSequence) return OFTrue;
+  if (key == DCM_TransducerBeamSteeringCodeSequence) return OFTrue;
+  if (key == DCM_TransducerApplicationCodeSequence) return OFTrue;
+  if (key == DCM_ProcessingFunction) return OFTrue;
+  if (key == DCM_MechanicalIndex) return OFTrue;
+  if (key == DCM_BoneThermalIndex) return OFTrue;
+  if (key == DCM_CranialThermalIndex) return OFTrue;
+  if (key == DCM_SoftTissueThermalIndex) return OFTrue;
+  if (key == DCM_DepthsOfFocus) return OFTrue;
+  if (key == DCM_DepthOfScanField) return OFTrue;
+
+  // any attributes of the Surface Segmentation module that are present
+  // if (key == DCM_InstanceNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentLabel) return OFTrue; // also in Raw Data Module
+  // if (key == DCM_ContentDescription) return OFTrue; // also in Raw Data Module
+  // if (key == DCM_ConceptNameCodeSequence) return OFTrue; // also in SR Document Content Module
+  if (key == DCM_AlternateContentDescriptionSequence) return OFTrue;
+  if (key == DCM_ContentCreatorName) return OFTrue;
+  if (key == DCM_ContentCreatorIdentificationCodeSequence) return OFTrue;
+  // if (key == DCM_ContentDate) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_SegmentSequence) return OFTrue; // also in Segmentation Image Module
 
-  /* Any attributes whose values are verifiable by the technician or physician 
+  // any attributes of the Surface Mesh Module that are present
+  if (key == DCM_NumberOfSurfaces) return OFTrue;
+  if (key == DCM_SurfaceSequence) return OFTrue;
+
+  // any attributes of the Structured Display module that are present
+  // if (key == DCM_InstanceNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentLabel) return OFTrue; // also in Raw Data Module
+  // if (key == DCM_ContentDescription) return OFTrue; // also in Raw Data Module
+  // if (key == DCM_ConceptNameCodeSequence) return OFTrue; // also in SR Document Content Module
+  // if (key == DCM_AlternateContentDescriptionSequence) return OFTrue; // also in Surface Segmentation Module
+  // if (key == DCM_ContentCreatorName) return OFTrue; // also in Surface Segmentation Module
+  // if (key == DCM_ContentCreatorIdentificationCodeSequence) return OFTrue; // also in Surface Segmentation Module
+  if (key == DCM_PresentationCreationDate) return OFTrue;
+  if (key == DCM_PresentationCreationTime) return OFTrue;
+  if (key == DCM_NumberOfScreens) return OFTrue;
+  if (key == DCM_NominalScreenDefinitionSequence) return OFTrue;
+  // if (key == DCM_IconImageSequence) return OFTrue; // also in General Image Module
+  if (key == DCM_StructuredDisplayBackgroundCIELabValue) return OFTrue;
+  if (key == DCM_EmptyImageBoxCIELabValue) return OFTrue;
+  if (key == DCM_HangingProtocolName) return OFTrue;
+  if (key == DCM_HangingProtocolCreator) return OFTrue;
+
+  // any attributes of the Structured Display Annotation module that are present
+  if (key == DCM_StructuredDisplayTextBoxSequence) return OFTrue;
+
+  // any attributes of the Structured Display Image Box module that are present
+  if (key == DCM_StructuredDisplayImageBoxSequence) return OFTrue;
+  if (key == DCM_ImageBoxSynchronizationSequence) return OFTrue;
+
+  // any Attributes of the Implant Template module that are present
+  if (key == DCM_Manufacturer) return OFTrue;
+  if (key == DCM_FrameOfReferenceUID) return OFTrue;
+  if (key == DCM_ImplantName) return OFTrue;
+  if (key == DCM_ImplantSize) return OFTrue;
+  if (key == DCM_ImplantPartNumber) return OFTrue;
+  if (key == DCM_ImplantTemplateVersion) return OFTrue;
+  if (key == DCM_ReplacedImplantTemplateSequence) return OFTrue;
+  if (key == DCM_ImplantType) return OFTrue;
+  if (key == DCM_OriginalImplantTemplateSequence) return OFTrue;
+  if (key == DCM_DerivationImplantTemplateSequence) return OFTrue;
+  if (key == DCM_EffectiveDateTime) return OFTrue;
+  if (key == DCM_ImplantTargetAnatomySequence) return OFTrue;
+  if (key == DCM_NotificationFromManufacturerSequence) return OFTrue;
+  if (key == DCM_InformationFromManufacturerSequence) return OFTrue;
+  if (key == DCM_ImplantRegulatoryDisapprovalCodeSequence) return OFTrue;
+  if (key == DCM_OverallTemplateSpatialTolerance) return OFTrue;
+  if (key == DCM_MaterialsCodeSequence) return OFTrue;
+  if (key == DCM_CoatingMaterialsCodeSequence) return OFTrue;
+  if (key == DCM_ImplantTypeCodeSequence) return OFTrue;
+  if (key == DCM_FixationMethodCodeSequence) return OFTrue;
+
+  // any Attributes of the Implant Assembly Template module that are present
+  // if (key == DCM_EffectiveDateTime) return OFTrue; // also in Implant Template Module
+  if (key == DCM_ImplantAssemblyTemplateName) return OFTrue;
+  if (key == DCM_ImplantAssemblyTemplateIssuer) return OFTrue;
+  if (key == DCM_ImplantAssemblyTemplateVersion) return OFTrue;
+  if (key == DCM_ReplacedImplantAssemblyTemplateSequence) return OFTrue;
+  if (key == DCM_ImplantAssemblyTemplateType) return OFTrue;
+  if (key == DCM_OriginalImplantAssemblyTemplateSequence) return OFTrue;
+  if (key == DCM_DerivationImplantAssemblyTemplateSequence) return OFTrue;
+  if (key == DCM_ImplantAssemblyTemplateTargetAnatomySequence) return OFTrue;
+  if (key == DCM_ProcedureTypeCodeSequence) return OFTrue;
+  if (key == DCM_SurgicalTechnique) return OFTrue;
+  // if (key == DCM_MIMETypeOfEncapsulatedDocument) return OFTrue; // also in Encapsulated Document Module
+  // if (key == DCM_EncapsulatedDocument) return OFTrue; // also in Encapsulated Document Module
+  if (key == DCM_ComponentTypesSequence) return OFTrue;
+  if (key == DCM_ComponentAssemblySequence) return OFTrue;
+
+  // any Attributes of the Implant Template Group module that are present
+  // if (key == DCM_EffectiveDateTime) return OFTrue; // also in Implant Template Module
+  if (key == DCM_ImplantTemplateGroupName) return OFTrue;
+  if (key == DCM_ImplantTemplateGroupDescription) return OFTrue;
+  if (key == DCM_ImplantTemplateGroupIssuer) return OFTrue;
+  if (key == DCM_ImplantTemplateGroupVersion) return OFTrue;
+  if (key == DCM_ReplacedImplantTemplateGroupSequence) return OFTrue;
+  if (key == DCM_ImplantTemplateGroupTargetAnatomySequence) return OFTrue;
+  if (key == DCM_ImplantTemplateGroupMembersSequence) return OFTrue;
+  if (key == DCM_ImplantTemplateGroupVariationDimensionSequence) return OFTrue;
+
+  // any attributes of the Point Cloud Module that are present
+  if (key == DCM_SurfacePointsSequence) return OFTrue;
+  if (key == DCM_SurfacePointPresentationValueData) return OFTrue;
+  if (key == DCM_SurfacePointColorCIELabValueData) return OFTrue;
+
+  // any attributes of the Enhanced Mammography Image module that are present
+  if (key == DCM_PositionerMotion) return OFTrue;
+  if (key == DCM_PositionerType) return OFTrue;
+  // if (key == DCM_ContentQualification) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_AcquisitionDateTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDuration) return OFTrue;  // also in Enhanced MR Image Module
+  if (key == DCM_KVP) return OFTrue;
+  if (key == DCM_XRayTubeCurrentInmA) return OFTrue;
+  if (key == DCM_ExposureTimeInms) return OFTrue;
+  if (key == DCM_ExposureInmAs) return OFTrue;
+  if (key == DCM_FocalSpots) return OFTrue;
+  if (key == DCM_AnodeTargetMaterial) return OFTrue;
+  if (key == DCM_BodyPartThickness) return OFTrue;
+  if (key == DCM_CompressionForce) return OFTrue;
+  if (key == DCM_CompressionPressure) return OFTrue;
+  if (key == DCM_CompressionContactArea) return OFTrue;
+  if (key == DCM_PaddleDescription) return OFTrue;
+  if (key == DCM_ExposureControlMode) return OFTrue;
+  if (key == DCM_ExposureControlModeDescription) return OFTrue;
+  if (key == DCM_PatientOrientation) return OFTrue;
+  // if (key == DCM_ImageComments) return OFTrue; // also in General Image Module
+  // if (key == DCM_SamplesPerPixel) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PhotometricInterpretation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsAllocated) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsStored) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_HighBit) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PixelRepresentation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_QualityControlImage) return OFTrue; // also in General Image Module
+  // if (key == DCM_BurnedInAnnotation) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompression) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionRatio) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionMethod) return OFTrue; // also in General Image Module
+  if (key == DCM_OrganDose) return OFTrue;
+  if (key == DCM_EntranceDoseInmGy) return OFTrue;
+  if (key == DCM_EntranceDoseDerivation) return OFTrue;
+  if (key == DCM_TypeOfDetectorMotion) return OFTrue;
+  // if (key == DCM_IconImageSequence) return OFTrue; // also in General Image Module
+  // if (key == DCM_PresentationLUTShape) return OFTrue; // also in General Image Module
+
+  // any attributes of the Volumetric Graphic Annotation Module that are present
+  if (key == DCM_VolumetricAnnotationSequence) return OFTrue;
+  if (key == DCM_VolumetricPresentationInputAnnotationSequence) return OFTrue;
+
+  /* Any attributes whose values are verifiable by the technician or physician
    * (e.g., their values are displayed to the technician or physician)
    * This is obviously application dependent. We don't handle that here.
-   */  
-  return OFFalse;    
+   */
+  return OFFalse;
+}
+
+
+OFBool SiAuthorizationProfile::checkRequiredAttributeList(DcmAttributeTag& tagList) const
+{
+  OFBool result =
+    containsTag(tagList, DCM_SOPClassUID) &&
+    containsTag(tagList, DCM_StudyInstanceUID) &&
+    containsTag(tagList, DCM_SeriesInstanceUID) &&
+    containsTag(tagList, DCM_SOPInstanceUID);
+
+  return result;
+}
+
+
+OFCondition SiAuthorizationProfile::inspectSignatureDataset(DcmItem &item)
+{
+  DcmElement *delem = NULL;
+  if (item.findAndGetElement(DCM_CreatorVersionUID, delem).good())
+  {
+    // The CreatorVersionUID attribute is present in the dataset or item.
+    // Since this attribute only occurs in the Raw Data Module, this means that
+    // the Raw Data Module is present.
+    containsRawData_ = OFTrue;
+  }
+  else
+  {
+    containsRawData_ = OFFalse;
+  }
+  return EC_Normal;
+}
+
+OFBool SiAuthorizationProfile::mainDatasetRequired() const
+{
+  return OFTrue;
 }
 
 #else /* WITH_OPENSSL */
index 073e45bbcd3dfe9c6858551d974f15d221a746d4..50c03f606bf83927b4362117f29c4726caf00554 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2010, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -35,8 +35,13 @@ OFBool SiBaseRSAProfile::isAllowableMACType(E_MACType macType) const
     case EMT_RIPEMD160:
     case EMT_SHA1:
     case EMT_MD5:
+    // support for the SHA2 hash algorithms was added in DICOM CP 1059.
+    case EMT_SHA256:
+    case EMT_SHA384:
+    case EMT_SHA512:
       result = OFTrue;
       break;
+
     default:
       /* nothing */
       break;
@@ -59,11 +64,16 @@ OFBool SiBaseRSAProfile::isAllowableAlgorithmType(E_KeyType keyType) const
   return result;
 }
 
-OFBool SiBaseRSAProfile::attributeRequired(const DcmTagKey& /* key */) const
+OFBool SiBaseRSAProfile::attributeRequiredIfPresent(const DcmTagKey& /* key */) const
 {
   return OFFalse;
 }
 
+OFBool SiBaseRSAProfile::checkRequiredAttributeList(DcmAttributeTag& /* tagList */) const
+{
+  return OFTrue;
+}
+
 OFBool SiBaseRSAProfile::attributeForbidden(const DcmTagKey& /* key */) const
 {
   return OFFalse;
@@ -75,6 +85,16 @@ OFBool SiBaseRSAProfile::isAllowableTransferSyntax(E_TransferSyntax xfer) const
   return OFTrue;
 }
 
+OFCondition SiBaseRSAProfile::inspectSignatureDataset(DcmItem & /* item */)
+{
+  return EC_Normal;
+}
+
+OFBool SiBaseRSAProfile::mainDatasetRequired() const
+{
+  return OFFalse;
+}
+
 #else /* WITH_OPENSSL */
 
 int sibrsapr_cc_dummy_to_keep_linker_from_moaning = 0;
index ea025fcdbb595362db0ba0c4a2135b102ae6a03f..9ea05d5d3cec23d98b0026c12d50dc78b9f45344 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2016, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 #include "dcmtk/dcmsign/sicert.h"
 #include "dcmtk/dcmsign/sirsa.h"   /* for class SiRSA */
 #include "dcmtk/dcmsign/sidsa.h"   /* for class SiDSA */
+#include "dcmtk/dcmsign/siecdsa.h" /* for class SiECDSA */
 #include "dcmtk/dcmdata/dcstack.h"
 #include "dcmtk/dcmdata/dcitem.h"
 #include "dcmtk/dcmdata/dcvrcs.h"
 #include "dcmtk/dcmdata/dcvrobow.h"
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/ofstd/ofdatime.h"
 
 BEGIN_EXTERN_C
 #include <openssl/evp.h>
 #include <openssl/x509.h>
 #include <openssl/pem.h>
+#include <openssl/err.h>
 END_EXTERN_C
 
-#if OPENSSL_VERSION_NUMBER < 0x10100000L
+#if OPENSSL_VERSION_NUMBER < 0x10100000L || defined(LIBRESSL_VERSION_NUMBER)
+#define X509_get0_notBefore(x) X509_get_notBefore(x)
+#define X509_get0_notAfter(x) X509_get_notAfter(x)
 #define EVP_PKEY_id(key) key->type
 #endif
 
+
 SiCertificate::SiCertificate()
 : x509(NULL)
 {
 }
 
+SiCertificate::SiCertificate(X509 *cert)
+: x509(cert)
+{
+}
+
 SiCertificate::~SiCertificate()
 {
-  if (x509) X509_free(x509);   
+  if (x509) X509_free(x509);
 }
 
 E_KeyType SiCertificate::getKeyType()
@@ -61,7 +72,7 @@ E_KeyType SiCertificate::getKeyType()
     EVP_PKEY *pkey = X509_extract_key(x509);
     if (pkey)
     {
-      switch(EVP_PKEY_id(pkey))
+      switch(EVP_PKEY_type(EVP_PKEY_id(pkey)))
       {
         case EVP_PKEY_RSA:
           result = EKT_RSA;
@@ -72,46 +83,57 @@ E_KeyType SiCertificate::getKeyType()
         case EVP_PKEY_DH:
           result = EKT_DH;
           break;
+        case EVP_PKEY_EC:
+          result = EKT_EC;
+          break;
         default:
           /* nothing */
           break;
       }
       EVP_PKEY_free(pkey);
-    }    
+    }
   }
   return result;
 }
 
 SiAlgorithm *SiCertificate::createAlgorithmForPublicKey()
 {
+  SiAlgorithm *result = NULL;
   if (x509)
   {
     EVP_PKEY *pkey = X509_extract_key(x509);
     if (pkey)
     {
-      switch(EVP_PKEY_id(pkey))
+      switch(EVP_PKEY_type(EVP_PKEY_id(pkey)))
       {
         case EVP_PKEY_RSA:
-          return new SiRSA(EVP_PKEY_get1_RSA(pkey));
-          /* break; */
+          result = new SiRSA(EVP_PKEY_get1_RSA(pkey));
+          break;
         case EVP_PKEY_DSA:
-          return new SiDSA(EVP_PKEY_get1_DSA(pkey));
-          /* break; */
+          result = new SiDSA(EVP_PKEY_get1_DSA(pkey));
+          break;
+        case EVP_PKEY_EC:
+#ifdef OPENSSL_NO_EC
+          result = new SiECDSA(NULL);
+#else
+          result = new SiECDSA(EVP_PKEY_get1_EC_KEY(pkey));
+#endif
+          break;
         case EVP_PKEY_DH:
         default:
           /* nothing */
           break;
       }
       EVP_PKEY_free(pkey);
-    }    
+    }
   }
-  return NULL;
+  return result;
 }
 
 OFCondition SiCertificate::loadCertificate(const char *filename, int filetype)
 {
-  OFCondition result = SI_EC_CannotRead;  
-  if (x509) X509_free(x509);   
+  OFCondition result = SI_EC_CannotRead;
+  if (x509) X509_free(x509);
   x509 = NULL;
   if (filename)
   {
@@ -139,6 +161,8 @@ OFCondition SiCertificate::loadCertificate(const char *filename, int filetype)
 OFCondition SiCertificate::read(DcmItem& item)
 {
   OFCondition result = EC_Normal;
+  if (x509) X509_free(x509);
+  x509 = NULL;
   OFString aString;
   DcmStack stack;
   result = item.search(DCM_CertificateType, stack, ESM_fromHere, OFFalse);
@@ -149,8 +173,8 @@ OFCondition SiCertificate::read(DcmItem& item)
     {
       if (aString == SI_DEFTERMS_X509CERT)
       {
-       stack.clear();
-       result = item.search(DCM_CertificateOfSigner, stack, ESM_fromHere, OFFalse);
+        stack.clear();
+        result = item.search(DCM_CertificateOfSigner, stack, ESM_fromHere, OFFalse);
         if (result.good())
         {
           DcmElement *cert = (DcmElement *)stack.top();
@@ -167,13 +191,35 @@ OFCondition SiCertificate::read(DcmItem& item)
 #else
               x509 = d2i_X509(NULL, &data, cert->getLength());
 #endif
-              if (x509 == NULL) result = EC_IllegalCall;              
-            } else result = EC_IllegalCall;            
-          }      
-        } 
-      } else result = EC_IllegalCall;
+              if (x509 == NULL)
+              {
+                DCMSIGN_WARN("Unable to parse X.509 certificate.");
+                result = SI_EC_VerificationFailed_NoCertificate;
+              }
+            }
+            else
+            {
+              DCMSIGN_WARN("Empty certificate of signer.");
+              result = SI_EC_VerificationFailed_NoCertificate;
+            }
+          }
+        }
+        else
+        {
+          DCMSIGN_WARN("Certificate missing in dataset.");
+          result = SI_EC_VerificationFailed_NoCertificate;
+        }
+      } else {
+        DCMSIGN_WARN("Encountered unsupported certificate type '" << aString << "' (expected '" << SI_DEFTERMS_X509CERT << "').");
+        result = SI_EC_VerificationFailed_NoCertificate;
+      }
     }
   }
+  else
+  {
+    DCMSIGN_WARN("Certificate type missing in dataset.");
+    result = SI_EC_VerificationFailed_NoCertificate;
+  }
   return result;
 }
 
@@ -259,7 +305,7 @@ void SiCertificate::getCertValidityNotBefore(OFString& str)
     BIO *certValidNotBeforeBIO = BIO_new(BIO_s_mem());
     if (certValidNotBeforeBIO)
     {
-      ASN1_UTCTIME_print(certValidNotBeforeBIO, X509_get_notBefore(x509));
+      ASN1_UTCTIME_print(certValidNotBeforeBIO, X509_get0_notBefore(x509));
       BIO_write(certValidNotBeforeBIO,"\0",1);
       BIO_get_mem_data(certValidNotBeforeBIO, (char *)(&bufptr));
       if (bufptr) str = bufptr;
@@ -277,7 +323,7 @@ void SiCertificate::getCertValidityNotAfter(OFString& str)
     BIO *certValidNotAfterBIO = BIO_new(BIO_s_mem());
     if (certValidNotAfterBIO)
     {
-      ASN1_UTCTIME_print(certValidNotAfterBIO, X509_get_notAfter(x509));
+      ASN1_UTCTIME_print(certValidNotAfterBIO, X509_get0_notAfter(x509));
       BIO_write(certValidNotAfterBIO,"\0",1);
       BIO_get_mem_data(certValidNotAfterBIO, (char *)(&bufptr));
       if (bufptr) str = bufptr;
@@ -286,6 +332,91 @@ void SiCertificate::getCertValidityNotAfter(OFString& str)
   }
 }
 
+OFBool SiCertificate::isCertExpiredAt(OFString& date)
+{
+  OFBool result = OFTrue;
+  if (x509)
+  {
+    const ASN1_TIME *certexpiry = X509_get0_notAfter(x509);
+    OFDateTime dt_certexpiry;
+    if (certexpiry && convertASN1Time(certexpiry, dt_certexpiry).good())
+    {
+      ASN1_TIME *sigdate = ASN1_TIME_new(); // ASN1_TIME is a typedef for ASN1_STRING
+      if (sigdate)
+      {
+        OFDateTime dt_sigdate;
+        if (ASN1_TIME_set_string(sigdate, date.c_str()) && convertASN1Time(sigdate, dt_sigdate).good())
+        {
+          // check if signature date is before certificate expiry
+          if (dt_sigdate < dt_certexpiry) result = OFFalse;
+        }
+        ASN1_TIME_free(sigdate);
+      }
+    }
+  }
+  return result;
+}
+
+OFBool SiCertificate::isCertNotYetValidAt(OFString& date)
+{
+  OFBool result = OFTrue;
+  if (x509)
+  {
+    const ASN1_TIME *certstart = X509_get0_notBefore(x509);
+    OFDateTime dt_certstart;
+    if (certstart && convertASN1Time(certstart, dt_certstart).good())
+    {
+      ASN1_TIME *sigdate = ASN1_TIME_new(); // ASN1_TIME is a typedef for ASN1_STRING
+      if (sigdate)
+      {
+        OFDateTime dt_sigdate;
+        if (ASN1_TIME_set_string(sigdate, date.c_str()) && convertASN1Time(sigdate, dt_sigdate).good())
+        {
+          // check if signature date is after certificate validity start
+          if (dt_sigdate > dt_certstart) result = OFFalse;
+        }
+        ASN1_TIME_free(sigdate);
+      }
+    }
+  }
+  return result;
+}
+
+
+OFBool SiCertificate::isCertExpiredNow() const
+{
+  OFBool result = OFTrue;
+  if (x509)
+  {
+    const ASN1_TIME *certexpiry = X509_get0_notAfter(x509);
+    if (certexpiry)
+    {
+      // X509_cmp_current_time() will return -1 when certexpiry is in the past
+      // and zero if there is an error. In both cases we treat the certificate as expired.
+      if (X509_cmp_current_time(certexpiry) > 0) result = OFFalse;
+    }
+  }
+  return result;
+}
+
+
+OFBool SiCertificate::isCertNotYetValidNow() const
+{
+  OFBool result = OFTrue;
+  if (x509)
+  {
+    const ASN1_TIME *certstart = X509_get0_notBefore(x509);
+    if (certstart)
+    {
+      // X509_cmp_current_time() will return 1 when certstart is in the future
+      // and zero if there is an error. In both cases we treat the certificate as invalid.
+      if (X509_cmp_current_time(certstart) < 0) result = OFFalse;
+    }
+  }
+  return result;
+}
+
+
 long SiCertificate::getCertKeyBits()
 {
   long certPubKeyBits = 0;                   /* certificate number of bits in public key */
@@ -301,6 +432,226 @@ long SiCertificate::getCertKeyBits()
   return certPubKeyBits;
 }
 
+const char *SiCertificate::getCertCurveName()
+{
+  const char *result = NULL;
+#ifndef OPENSSL_NO_EC
+  if (x509)
+  {
+    EVP_PKEY *pkey = X509_extract_key(x509);
+    if (pkey && EVP_PKEY_type(EVP_PKEY_id(pkey)) == EVP_PKEY_EC)
+    {
+      // we have an elliptic curve. Access EC key.
+#if OPENSSL_VERSION_NUMBER < 0x10100000L || defined(LIBRESSL_VERSION_NUMBER)
+      EC_KEY *eckey = EVP_PKEY_get1_EC_KEY(pkey);
+#else
+      const EC_KEY *eckey = EVP_PKEY_get0_EC_KEY(pkey);
+#endif
+      if (eckey)
+      {
+        // access EC group within EC key
+        const EC_GROUP *ecgroup = EC_KEY_get0_group(eckey);
+        if (ecgroup)
+        {
+          // check if we have a named curve
+          int nid = EC_GROUP_get_curve_name(ecgroup);
+          if (nid > 0)
+          {
+            result = OBJ_nid2sn(nid);
+          }
+          else result = "unnamed curve";
+        }
+#if OPENSSL_VERSION_NUMBER < 0x10100000L || defined(LIBRESSL_VERSION_NUMBER)
+        EC_KEY_free(eckey);
+#endif
+      }
+      EVP_PKEY_free(pkey);
+    }
+  }
+#endif
+  return result;
+}
+
+OFBool SiCertificate::isWeakKey()
+{
+  OFBool result = OFTrue;
+  long bits = getCertKeyBits();
+  switch (getKeyType())
+  {
+    case EKT_RSA:
+    case EKT_DSA:
+    case EKT_DH:
+      if (bits >= 1024) result = OFFalse;
+      break;
+    case EKT_EC:
+      if (bits >= 256) result = OFFalse;
+      break;
+    case EKT_none: // should never happen
+      break;
+  }
+  return result;
+}
+
+void SiCertificate::checkForWeakKey()
+{
+  if (isWeakKey())
+  {
+    switch (getKeyType())
+    {
+      case EKT_RSA:
+        DCMSIGN_WARN("Certificate contains a weak key: RSA, " << getCertKeyBits() << " bits");
+        break;
+      case EKT_DSA:
+        DCMSIGN_WARN("Certificate contains a weak key: DSA, " << getCertKeyBits() << " bits");
+        break;
+      case EKT_EC:
+        DCMSIGN_WARN("Certificate contains a weak key: EC, " << getCertKeyBits() << " bits");
+        break;
+      case EKT_DH:
+        DCMSIGN_WARN("Certificate contains a weak key: DH, " << getCertKeyBits() << " bits");
+        break;
+      case EKT_none: // should never happen
+        DCMSIGN_WARN("Certificate contains a weak key: unknown type");
+        break;
+    }
+  }
+}
+
+OFCondition SiCertificate::convertGeneralizedTime(const ASN1_GENERALIZEDTIME *d, OFDateTime& dt)
+{
+    // This method is derived from OpenSSL's asn1_generalizedtime_to_tm(),
+    // which was introduced in OpenSSL 1.0.2. Since we still support OpenSSL 1.0.1,
+    // we cannot use that function.
+
+    static const int minval[9] = { 0, 0, 1, 1, 0, 0, 0, 0, 0 };
+    static const int maxval[9] = { 99, 99, 12, 31, 23, 59, 59, 12, 59 };
+
+    unsigned int dt_year = 0;
+    unsigned int dt_month = 0;
+    unsigned int dt_day = 0;
+    unsigned int dt_hour = 0;
+    unsigned int dt_minute = 0;
+    double dt_second = 0.0;
+    double dt_timeZone = 0.0;
+    char *a;
+    int n, i, l, o;
+
+    if (d == NULL) return EC_IllegalCall;
+    if (d->type != V_ASN1_GENERALIZEDTIME) return EC_IllegalCall;
+    l = d->length;
+    a = (char *)d->data;
+    o = 0;
+    /*
+     * GENERALIZEDTIME is similar to UTCTIME except the year is represented
+     * as YYYY. This stuff treats everything as a two digit field so make
+     * first two fields 00 to 99
+     */
+    if (l < 13) return EC_IllegalCall;
+    for (i = 0; i < 7; i++) {
+        if ((i == 6) && ((a[o] == 'Z') || (a[o] == '+') || (a[o] == '-'))) {
+            i++;
+            dt_second = 0;
+            break;
+        }
+        if ((a[o] < '0') || (a[o] > '9')) return EC_IllegalCall;
+        n = a[o] - '0';
+        if (++o > l) return EC_IllegalCall;
+
+        if ((a[o] < '0') || (a[o] > '9')) return EC_IllegalCall;
+        n = (n * 10) + a[o] - '0';
+        if (++o > l) return EC_IllegalCall;
+
+        if ((n < minval[i]) || (n > maxval[i])) return EC_IllegalCall;
+        switch (i)
+       {
+          case 0:
+            dt_year = n * 100;
+            break;
+          case 1:
+            dt_year += n;
+            break;
+          case 2:
+            dt_month = n;
+            break;
+          case 3:
+            dt_day = n;
+            break;
+          case 4:
+            dt_hour = n;
+            break;
+          case 5:
+            dt_minute = n;
+            break;
+          case 6:
+            dt_second = n;
+            break;
+        }
+    }
+    /*
+     * Optional fractional seconds: decimal point followed by one or more
+     * digits.
+     */
+    if (a[o] == '.') {
+        if (++o > l) return EC_IllegalCall;
+        i = o;
+        while ((a[o] >= '0') && (a[o] <= '9') && (o <= l)) o++;
+        /* Must have at least one digit after decimal point */
+        if (i == o) return EC_IllegalCall;
+    }
+
+    if (a[o] == 'Z')
+        o++;
+    else if ((a[o] == '+') || (a[o] == '-')) {
+        int offsign = a[o] == '-' ? 1 : -1, offset = 0;
+        o++;
+        if (o + 4 > l)
+            return EC_IllegalCall;
+        for (i = 7; i < 9; i++) {
+            if ((a[o] < '0') || (a[o] > '9')) return EC_IllegalCall;
+            n = a[o] - '0';
+            o++;
+            if ((a[o] < '0') || (a[o] > '9')) return EC_IllegalCall;
+            n = (n * 10) + a[o] - '0';
+            if ((n < minval[i]) || (n > maxval[i])) return EC_IllegalCall;
+            if (i == 7)
+                offset = n * 3600;
+            else if (i == 8)
+                offset += n * 60;
+            o++;
+        }
+        if (offset) dt_timeZone = offset / 3600.0 * offsign;
+    } else if (a[o]) {
+        /* Missing time zone information. */
+        return EC_IllegalCall;
+    }
+    if (! dt.setDateTime(dt_year, dt_month, dt_day, dt_hour, dt_minute, dt_second, dt_timeZone)) return EC_IllegalCall;
+
+    return ((o == l) ? EC_Normal : EC_IllegalCall);
+}
+
+
+OFCondition SiCertificate::convertASN1Time(const ASN1_TIME *d, OFDateTime& dt)
+{
+  if (d)
+  {
+#if OPENSSL_VERSION_NUMBER < 0x10100000L || defined(LIBRESSL_VERSION_NUMBER)
+    // Before OpenSSL 1.1.0, the first parameter of ASN1_TIME_to_generalizedtime()
+    // was not declared const, as it should be
+    ASN1_GENERALIZEDTIME *gm = ASN1_TIME_to_generalizedtime(OFconst_cast(ASN1_TIME *, d), NULL);
+#else
+    ASN1_GENERALIZEDTIME *gm = ASN1_TIME_to_generalizedtime(d, NULL);
+#endif
+    if (gm)
+    {
+      OFCondition result = convertGeneralizedTime(gm, dt);
+      ASN1_GENERALIZEDTIME_free(gm);
+      return result;
+    }
+  }
+  return EC_IllegalCall;
+}
+
+
 #else /* WITH_OPENSSL */
 
 int sicert_cc_dummy_to_keep_linker_from_moaning = 0;
index 5de5efb99cbccc02d16bd2d04764774448edeaa7..92a775e090d2e87401947b9a456d4f5a9b87e94a 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2017, OFFIS e.V.
+ *  Copyright (C) 1998-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -35,14 +35,31 @@ END_EXTERN_C
 
 SiCertificateVerifier::SiCertificateVerifier()
 : x509store(NULL)
+, x509untrusted(NULL)
+, enableCRLverification(OFFalse)
 , errorCode(0)
 {
   x509store = X509_STORE_new();
+  x509untrusted = sk_X509_new_null();
 }
 
+
 SiCertificateVerifier::~SiCertificateVerifier()
 {
-  if (x509store) X509_STORE_free(x509store);
+  X509_STORE_free(x509store);
+  sk_X509_pop_free(x509untrusted, X509_free);
+}
+
+
+X509_STORE *SiCertificateVerifier::getTrustedCertStore()
+{
+  return x509store;
+}
+
+
+stack_st_X509 *SiCertificateVerifier::getUntrustedCerts()
+{
+  return x509untrusted;
 }
 
 
@@ -56,6 +73,56 @@ OFCondition SiCertificateVerifier::addTrustedCertificateFile(const char *fileNam
 }
 
 
+OFCondition SiCertificateVerifier::addUntrustedCertificateFile(const char *fileName, int fileType)
+{
+  OFCondition result = EC_Normal;
+  if (x509untrusted)
+  {
+    // PEM has different loading code because a PEM file can contain several certificates and CRLs
+    if (fileType == X509_FILETYPE_PEM)
+    {
+      BIO *bio = BIO_new_file(fileName, "r");
+      if (bio)
+      {
+        STACK_OF(X509_INFO) *x509infostack = PEM_X509_INFO_read_bio(bio, NULL, NULL, NULL);
+        if (x509infostack)
+        {
+          for (int i = 0; i < sk_X509_INFO_num(x509infostack); i++)
+          {
+            X509_INFO *xi = sk_X509_INFO_value(x509infostack, i);
+            if (xi->x509)
+            {
+              // move certificate to our list of untrusted certificates
+              sk_X509_push(x509untrusted, xi->x509);
+              xi->x509 = NULL;
+            }
+          }
+          // delete the remaining x509infostack
+          sk_X509_INFO_pop_free(x509infostack, X509_INFO_free);
+        } else result = SI_EC_CannotRead;
+        BIO_free(bio);
+      } else result = SI_EC_CannotRead;
+    }
+    else if (fileType == X509_FILETYPE_ASN1)
+    {
+      // load a single certificate in ASN.1 DER format
+      BIO *bio = BIO_new_file(fileName, "rb");
+      if (bio)
+      {
+        X509 *xcert = d2i_X509_bio(bio, NULL);
+        if (xcert)
+        {
+          sk_X509_push(x509untrusted, xcert);
+        } else result = SI_EC_CannotRead;
+        BIO_free(bio);
+      } else result = SI_EC_CannotRead;
+    } else result = SI_EC_InvalidFiletype;
+  } else result = SI_EC_CannotRead;
+
+  return result;
+}
+
+
 OFCondition SiCertificateVerifier::addTrustedCertificateDir(const char *pathName, int fileType)
 {
   /* fileType should be X509_FILETYPE_PEM or X509_FILETYPE_ASN1 */
@@ -80,18 +147,15 @@ OFCondition SiCertificateVerifier::addCertificateRevocationList(const char *file
         if (fileType == X509_FILETYPE_ASN1)
         {
           x509crl = d2i_X509_CRL_bio(in, NULL);
-          if (x509crl)
-          {
-            X509_STORE_add_crl(x509store, x509crl);
-            result = EC_Normal;
-          }
         } else {
           x509crl = PEM_read_bio_X509_CRL(in, NULL, NULL, NULL);
-          if (x509crl)
-          {
-            X509_STORE_add_crl(x509store, x509crl);
-            result = EC_Normal;
-          }
+        }
+        if (x509crl)
+        {
+          X509_STORE_add_crl(x509store, x509crl); // creates a copy of the CRL object
+          X509_CRL_free(x509crl);
+          enableCRLverification = OFTrue;
+          result = EC_Normal;
         }
       }
       BIO_free(in);
@@ -101,6 +165,31 @@ OFCondition SiCertificateVerifier::addCertificateRevocationList(const char *file
 }
 
 
+void SiCertificateVerifier::setCRLverification(OFBool enabled)
+{
+  enableCRLverification = enabled;
+}
+
+
+extern "C"
+{
+  int sicertvf_verify_callback(int deflt, X509_STORE_CTX *ctx);
+}
+
+int sicertvf_verify_callback(int deflt, X509_STORE_CTX *ctx)
+{
+  if (ctx)
+  {
+    void *p = X509_STORE_CTX_get_ex_data(ctx, 0);
+    if (p)
+    {
+      SiCertificateVerifier *pthis = OFreinterpret_cast(SiCertificateVerifier *, p);
+      return pthis->verifyCallback(deflt, ctx);
+    }
+  }
+  return deflt;
+}
+
 OFCondition SiCertificateVerifier::verifyCertificate(SiCertificate& certificate)
 {
   errorCode = 0;
@@ -108,7 +197,22 @@ OFCondition SiCertificateVerifier::verifyCertificate(SiCertificate& certificate)
   if (rawcert == NULL) return SI_EC_VerificationFailed_NoCertificate;
 
   X509_STORE_CTX *ctx = X509_STORE_CTX_new();
-  X509_STORE_CTX_init(ctx, x509store, rawcert, NULL);
+  X509_STORE_CTX_init(ctx, x509store, rawcert, x509untrusted);
+
+  X509_VERIFY_PARAM *param = X509_VERIFY_PARAM_new();
+  if (param)
+  {
+    if (enableCRLverification)
+    {
+      // enable CRL checking for the signer certificate
+      X509_VERIFY_PARAM_set_flags(param, X509_V_FLAG_CRL_CHECK);
+    }
+    X509_VERIFY_PARAM_set_depth(param, 100); // that's the OpenSSL default
+    X509_STORE_CTX_set0_param(ctx, param);
+  }
+
+  X509_STORE_CTX_set_ex_data(ctx, 0, OFreinterpret_cast(void *, this));
+  X509_STORE_CTX_set_verify_cb(ctx, sicertvf_verify_callback);
 
   // If a complete chain can be built and validated X509_verify_cert() returns 1,
   // otherwise it returns zero, in exceptional circumstances it can also return a negative code.
@@ -121,6 +225,25 @@ OFCondition SiCertificateVerifier::verifyCertificate(SiCertificate& certificate)
   if (ok == 1) return EC_Normal; else return SI_EC_VerificationFailed_NoTrust;
 }
 
+int SiCertificateVerifier::verifyCallback(int deflt, X509_STORE_CTX *ctx)
+{
+  if (X509_STORE_CTX_get_error(ctx) == X509_V_ERR_CERT_REVOKED)
+  {
+     // The signer certificate is on the revocation list. By default, this means that
+     // the certificate verification will fail, independent from the timestamp of the signature
+     // and the timestamp of the revocation. At this point we could add additional code that
+     // compares the time of revocation with the DICOM signature datetime or (preferrably) a
+     // certified timestamp that might also be present. If the revocation occured after the time of
+     // signature, we could still accept the certificate and thus the signature.
+     // For now, we retain the OpenSSL default behaviour.
+  }
+  return deflt;
+}
+
+OFBool SiCertificateVerifier::lastErrorIsCertExpiry() const
+{
+  return (errorCode == X509_V_ERR_CERT_HAS_EXPIRED);
+}
 
 const char *SiCertificateVerifier::lastError() const
 {
index 843f1042e34bd9678a9163075d614a8b5bbb0bf8..9584d9606616cc85b6ff686b063868664f6661fc 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2010, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
 
 #include "dcmtk/dcmsign/sicreapr.h"
 #include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmdata/dcitem.h"
+#include "dcmtk/dcmsign/sitypes.h"
 
+SiCreatorProfile::SiCreatorProfile()
+: containsRawData_(OFFalse)
+{
+}
 
-OFBool SiCreatorProfile::attributeRequired(const DcmTagKey& key) const
+OFBool SiCreatorProfile::attributeRequiredIfPresent(const DcmTagKey& key) const
 {
-  /* SOP Class and Instance UIDs */
+  // This list of attribute tags was extracted from DICOM 2019c.
+  // Attribute tags occuring in multiple modules were commented out
+  // but remain in the source code to simplify a comparison with the
+  // module tables in a later edition of the DICOM standard.
+
+  // The following attributes must be included in the signature if present
+  // according to the Creator RSA Digital Signature Profile
+  // (DICOM Part 15, section C.2):
+
+  // the SOP Class and Instance UIDs
   if (key == DCM_SOPClassUID) return OFTrue;
   if (key == DCM_SOPInstanceUID) return OFTrue;
 
-  /* SOP Creation Date and Time, if present */
+  // the SOP Creation Date and Time, if present
   if (key == DCM_InstanceCreationDate) return OFTrue;
   if (key == DCM_InstanceCreationTime) return OFTrue;
 
-  /* Study and Series Instance UIDs */
+  // the Study and Series Instance UIDs
   if (key == DCM_StudyInstanceUID) return OFTrue;
   if (key == DCM_SeriesInstanceUID) return OFTrue;
 
-  /* Any attributes of the General Equipment module that are present */
-
+  // any attributes of the General Equipment Module that are present
   if (key == DCM_Manufacturer) return OFTrue;
   if (key == DCM_InstitutionName) return OFTrue;
   if (key == DCM_InstitutionAddress) return OFTrue;
   if (key == DCM_StationName) return OFTrue;
   if (key == DCM_InstitutionalDepartmentName) return OFTrue;
+  if (key == DCM_InstitutionalDepartmentTypeCodeSequence) return OFTrue;
   if (key == DCM_ManufacturerModelName) return OFTrue;
   if (key == DCM_DeviceSerialNumber) return OFTrue;
   if (key == DCM_SoftwareVersions) return OFTrue;
+  if (key == DCM_GantryID) return OFTrue;
+  if (key == DCM_UDISequence) return OFTrue;
+  if (key == DCM_DeviceUID) return OFTrue;
   if (key == DCM_SpatialResolution) return OFTrue;
   if (key == DCM_DateOfLastCalibration) return OFTrue;
   if (key == DCM_TimeOfLastCalibration) return OFTrue;
   if (key == DCM_PixelPaddingValue) return OFTrue;
 
-  /* Any overlay data present */
-  if ((key.getGroup() >= 0x6000) && (key.getGroup() < 0x6020) && ((key.getGroup() & 0x0001) == 0)) return OFTrue;
+  // any attributes of the Overlay Plane Module that are present
+  if (key == DCM_OverlayRows) return OFTrue;
+  if (key == DCM_OverlayColumns) return OFTrue;
+  if (key == DCM_OverlayType) return OFTrue;
+  if (key == DCM_OverlayOrigin) return OFTrue;
+  if (key == DCM_OverlayBitsAllocated) return OFTrue;
+  if (key == DCM_OverlayBitPosition) return OFTrue;
+  if (key == DCM_OverlayData) return OFTrue;
+  if (key == DCM_OverlayDescription) return OFTrue;
+  if (key == DCM_OverlaySubtype) return OFTrue;
+  if (key == DCM_OverlayLabel) return OFTrue;
+  if (key == DCM_ROIArea) return OFTrue;
+  if (key == DCM_ROIMean) return OFTrue;
+  if (key == DCM_ROIStandardDeviation) return OFTrue;
 
-  /* Any image data present - we assume this means the Image Pixel Module and not just PixelData */
-  if (key.getGroup() == 0x0028)
+  // any attributes of the Curve Module that are present
+  if ((key.getGroup() >= 0x5000) && (key.getGroup() < 0x5020) && ((key.getGroup() & 1) == 0))
   {
-    Uint16 elem = key.getElement();
-    if (elem == 0x0002) return OFTrue; // DCM_SamplesPerPixel
-    if (elem == 0x0004) return OFTrue; // DCM_PhotometricInterpretation
-    if (elem == 0x0006) return OFTrue; // DCM_PlanarConfiguration
-    if (elem == 0x0010) return OFTrue; // DCM_Rows
-    if (elem == 0x0011) return OFTrue; // DCM_Columns
-    if (elem == 0x0034) return OFTrue; // DCM_PixelAspectRatio
-    if (elem == 0x0100) return OFTrue; // DCM_BitsAllocated
-    if (elem == 0x0101) return OFTrue; // DCM_BitsStored
-    if (elem == 0x0102) return OFTrue; // DCM_HighBit
-    if (elem == 0x0103) return OFTrue; // DCM_PixelRepresentation
-    if (elem == 0x0106) return OFTrue; // DCM_SmallestImagePixelValue
-    if (elem == 0x0107) return OFTrue; // DCM_LargestImagePixelValue
-    if (elem == 0x1101) return OFTrue; // DCM_RedPaletteColorLookupTableDescriptor
-    if (elem == 0x1102) return OFTrue; // DCM_GreenPaletteColorLookupTableDescriptor
-    if (elem == 0x1103) return OFTrue; // DCM_BluePaletteColorLookupTableDescriptor
-    if (elem == 0x1201) return OFTrue; // DCM_RedPaletteColorLookupTableData
-    if (elem == 0x1202) return OFTrue; // DCM_GreenPaletteColorLookupTableData
-    if (elem == 0x1203) return OFTrue; // DCM_BluePaletteColorLookupTableData
+    switch (key.getElement())
+    {
+      case 0x0005: // CurveDimensions (retired)
+      case 0x0010: // NumberOfPoints (retired)
+      case 0x0103: // DataValueRepresentation (retired)
+      case 0x3000: // CurveData (retired)
+      case 0x0022: // CurveDescription (retired)
+      case 0x0030: // AxisUnits (retired)
+      case 0x0040: // AxisLabels (retired)
+      case 0x0104: // MinimumCoordinateValue (retired)
+      case 0x0105: // MaximumCoordinateValue (retired)
+      case 0x0106: // CurveRange (retired)
+      case 0x0110: // CurveDataDescriptor (retired)
+      case 0x0112: // CoordinateStartValue (retired)
+      case 0x0114: // CoordinateStepValue (retired)
+      case 0x2500: // CurveLabel (retired)
+      case 0x2600: // ReferencedOverlaySequence (retired)
+        return OFTrue;
+        break;
+      default:
+        /* nothing */
+        break;
+    }
   }
+
+  // any attributes of the Graphic Annotation Module that are present
+  if (key == DCM_GraphicAnnotationSequence) return OFTrue;
+
+  // any attributes of the General Image Module that are present
+  if (key == DCM_InstanceNumber) return OFTrue;
+  if (key == DCM_PatientOrientation) return OFTrue;
+  if (key == DCM_ContentDate) return OFTrue;
+  if (key == DCM_ContentTime) return OFTrue;
+  if (key == DCM_ImageType) return OFTrue;
+  if (key == DCM_AcquisitionNumber) return OFTrue;
+  if (key == DCM_AcquisitionDate) return OFTrue;
+  if (key == DCM_AcquisitionTime) return OFTrue;
+  if (key == DCM_AcquisitionDateTime) return OFTrue;
+  if (key == DCM_ImagesInAcquisition) return OFTrue;
+  if (key == DCM_ImageComments) return OFTrue;
+  if (key == DCM_QualityControlImage) return OFTrue;
+  if (key == DCM_BurnedInAnnotation) return OFTrue;
+  if (key == DCM_RecognizableVisualFeatures) return OFTrue;
+  if (key == DCM_LossyImageCompression) return OFTrue;
+  if (key == DCM_LossyImageCompressionRatio) return OFTrue;
+  if (key == DCM_LossyImageCompressionMethod) return OFTrue;
+  if (key == DCM_IconImageSequence) return OFTrue;
+  if (key == DCM_PresentationLUTShape) return OFTrue;
+  if (key == DCM_IrradiationEventUID) return OFTrue;
+  if (key == DCM_RealWorldValueMappingSequence) return OFTrue;
+  if (key == DCM_ImageLaterality) return OFTrue;
+  if (key == DCM_AnatomicRegionSequence) return OFTrue;
+  if (key == DCM_PrimaryAnatomicStructureSequence) return OFTrue;
+
+  // any attributes of the Image Pixel Module that are present
+  if (key == DCM_SamplesPerPixel) return OFTrue;
+  if (key == DCM_PhotometricInterpretation) return OFTrue;
+  if (key == DCM_Rows) return OFTrue;
+  if (key == DCM_Columns) return OFTrue;
+  if (key == DCM_BitsAllocated) return OFTrue;
+  if (key == DCM_BitsStored) return OFTrue;
+  if (key == DCM_HighBit) return OFTrue;
+  if (key == DCM_PixelRepresentation) return OFTrue;
+  if (key == DCM_PlanarConfiguration) return OFTrue;
+  if (key == DCM_PixelAspectRatio) return OFTrue;
+  if (key == DCM_SmallestImagePixelValue) return OFTrue;
+  if (key == DCM_LargestImagePixelValue) return OFTrue;
+  if (key == DCM_RedPaletteColorLookupTableDescriptor) return OFTrue;
+  if (key == DCM_GreenPaletteColorLookupTableDescriptor) return OFTrue;
+  if (key == DCM_BluePaletteColorLookupTableDescriptor) return OFTrue;
+  if (key == DCM_RedPaletteColorLookupTableData) return OFTrue;
+  if (key == DCM_GreenPaletteColorLookupTableData) return OFTrue;
+  if (key == DCM_BluePaletteColorLookupTableData) return OFTrue;
+  if (key == DCM_ICCProfile) return OFTrue;
+  if (key == DCM_ColorSpace) return OFTrue;
   if (key == DCM_PixelData) return OFTrue;
+  if (key == DCM_PixelDataProviderURL) return OFTrue;
+  if (key == DCM_PixelPaddingRangeLimit) return OFTrue;
+  if (key == DCM_ExtendedOffsetTable) return OFTrue;
+  if (key == DCM_ExtendedOffsetTableLengths) return OFTrue;
+
+  // any attributes of the SR Document General Module that are present
+  // if (key == DCM_InstanceNumber) return OFTrue; // also in General Image Module
+  if (key == DCM_PreliminaryFlag) return OFTrue;
+  if (key == DCM_CompletionFlag) return OFTrue;
+  if (key == DCM_CompletionFlagDescription) return OFTrue;
+  if (key == DCM_VerificationFlag) return OFTrue;
+  // if (key == DCM_ContentDate) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentTime) return OFTrue; // also in General Image Module
+  if (key == DCM_VerifyingObserverSequence) return OFTrue;
+  if (key == DCM_AuthorObserverSequence) return OFTrue;
+  if (key == DCM_ParticipantSequence) return OFTrue;
+  if (key == DCM_CustodialOrganizationSequence) return OFTrue;
+  if (key == DCM_PredecessorDocumentsSequence) return OFTrue;
+  if (key == DCM_IdenticalDocumentsSequence) return OFTrue;
+  if (key == DCM_ReferencedRequestSequence) return OFTrue;
+  if (key == DCM_PerformedProcedureCodeSequence) return OFTrue;
+  if (key == DCM_CurrentRequestedProcedureEvidenceSequence) return OFTrue;
+  if (key == DCM_PertinentOtherEvidenceSequence) return OFTrue;
+  if (key == DCM_ReferencedInstanceSequence) return OFTrue;
+
+  // any attributes of the SR Document Content Module that are present
+  if (key == DCM_ValueType) return OFTrue;
+  if (key == DCM_ConceptNameCodeSequence) return OFTrue;
+  if (key == DCM_ContinuityOfContent) return OFTrue;
+  if (key == DCM_ContentTemplateSequence) return OFTrue;
+  if (key == DCM_ObservationDateTime) return OFTrue;
+  if (key == DCM_ObservationUID) return OFTrue;
+  if (key == DCM_ContentSequence) return OFTrue;
+
+  // any attributes of the Waveform Module that are present
+  if (key == DCM_WaveformSequence) return OFTrue;
+  if (key == DCM_WaveformDataDisplayScale) return OFTrue;
+  if (key == DCM_WaveformDisplayBackgroundCIELabValue) return OFTrue;
+  if (key == DCM_WaveformPresentationGroupSequence) return OFTrue;
+
+  // any attributes of the Waveform Annotation Module that are present
+  if (key == DCM_WaveformAnnotationSequence) return OFTrue;
+
+  // any attributes of the Multi-frame Functional Groups Module that are present
+  if (key == DCM_SharedFunctionalGroupsSequence) return OFTrue;
+  if (key == DCM_PerFrameFunctionalGroupsSequence) return OFTrue;
+  // if (key == DCM_InstanceNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentDate) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentTime) return OFTrue; // also in General Image Module
+  if (key == DCM_NumberOfFrames) return OFTrue;
+  if (key == DCM_StereoPairsPresent) return OFTrue;
+  if (key == DCM_ConcatenationFrameOffsetNumber) return OFTrue;
+  if (key == DCM_RepresentativeFrameNumber) return OFTrue;
+  if (key == DCM_ConcatenationUID) return OFTrue;
+  if (key == DCM_SOPInstanceUIDOfConcatenationSource) return OFTrue;
+  if (key == DCM_InConcatenationNumber) return OFTrue;
+  if (key == DCM_InConcatenationTotalNumber) return OFTrue;
+
+  // any attributes of the Enhanced MR Image Module that are present
+  // if (key == DCM_AcquisitionNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDateTime) return OFTrue; // also in General Image Module
+  if (key == DCM_AcquisitionDuration) return OFTrue;
+  if (key == DCM_ReferencedRawDataSequence) return OFTrue;
+  if (key == DCM_ReferencedWaveformSequence) return OFTrue;
+  if (key == DCM_ReferencedImageEvidenceSequence) return OFTrue;
+  if (key == DCM_SourceImageEvidenceSequence) return OFTrue;
+  if (key == DCM_ReferencedPresentationStateSequence) return OFTrue;
+  if (key == DCM_ContentQualification) return OFTrue;
+  if (key == DCM_ResonantNucleus) return OFTrue;
+  if (key == DCM_KSpaceFiltering) return OFTrue;
+  if (key == DCM_MagneticFieldStrength) return OFTrue;
+  if (key == DCM_ApplicableSafetyStandardAgency) return OFTrue;
+  if (key == DCM_ApplicableSafetyStandardDescription) return OFTrue;
+  // if (key == DCM_ImageComments) return OFTrue; // also in General Image Module
+  if (key == DCM_IsocenterPosition) return OFTrue;
+  if (key == DCM_B1rms) return OFTrue;
+  // if (key == DCM_ImageType) return OFTrue; // also in General Image Module
+  if (key == DCM_PixelPresentation) return OFTrue;
+  if (key == DCM_VolumetricProperties) return OFTrue;
+  if (key == DCM_VolumeBasedCalculationTechnique) return OFTrue;
+  if (key == DCM_ComplexImageComponent) return OFTrue;
+  if (key == DCM_AcquisitionContrast) return OFTrue;
+  if (key == DCM_FunctionalSettlingPhaseFramesPresent) return OFTrue;
+  // if (key == DCM_SamplesPerPixel) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PhotometricInterpretation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsAllocated) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsStored) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_HighBit) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PixelRepresentation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PlanarConfiguration) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BurnedInAnnotation) return OFTrue; // also in General Image Module
+  // if (key == DCM_RecognizableVisualFeatures) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompression) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionRatio) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionMethod) return OFTrue; // also in General Image Module
+  // if (key == DCM_PresentationLUTShape) return OFTrue; // also in General Image Module
+  // if (key == DCM_IconImageSequence) return OFTrue; // also in General Image Module
+  if (key == DCM_ViewCodeSequence) return OFTrue;
+  if (key == DCM_SliceProgressionDirection) return OFTrue;
+
+  // any attributes of the MR Spectroscopy Module that are present
+  // if (key == DCM_AcquisitionNumber) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_AcquisitionDateTime) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_AcquisitionDuration) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedRawDataSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedWaveformSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_SourceImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedPresentationStateSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ContentQualification) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ResonantNucleus) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_k-SpaceFiltering) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_MagneticFieldStrength) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ApplicableSafetyStandardAgency) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ApplicableSafetyStandardDescription) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ImageComments) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_IsocenterPosition) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_B1rms) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ImageType) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_VolumetricProperties) return OFTrue; // also in Enhanced MR Image Module
+  // if (key == DCM_VolumeBasedCalculationTechnique) return OFTrue; // also in Enhanced MR Image Module
+  // if (key == DCM_ComplexImageComponent) return OFTrue; // also in Enhanced MR Image Module
+  // if (key == DCM_AcquisitionContrast) return OFTrue; // also in Enhanced MR Image Module
+  if (key == DCM_TransmitterFrequency) return OFTrue;
+  if (key == DCM_SpectralWidth) return OFTrue;
+  if (key == DCM_ChemicalShiftReference) return OFTrue;
+  if (key == DCM_VolumeLocalizationTechnique) return OFTrue;
+  if (key == DCM_VolumeLocalizationSequence) return OFTrue;
+  if (key == DCM_Decoupling) return OFTrue;
+  if (key == DCM_DecoupledNucleus) return OFTrue;
+  if (key == DCM_DecouplingFrequency) return OFTrue;
+  if (key == DCM_DecouplingMethod) return OFTrue;
+  if (key == DCM_DecouplingChemicalShiftReference) return OFTrue;
+  if (key == DCM_TimeDomainFiltering) return OFTrue;
+  if (key == DCM_NumberOfZeroFills) return OFTrue;
+  if (key == DCM_BaselineCorrection) return OFTrue;
+  if (key == DCM_FrequencyCorrection) return OFTrue;
+  if (key == DCM_FirstOrderPhaseCorrection) return OFTrue;
+  if (key == DCM_WaterReferencedPhaseCorrection) return OFTrue;
+  if (key == DCM_WaterReferenceAcquisition) return OFTrue;
+  // if (key == DCM_ReferencedInstanceSequence) return OFTrue; // also in SR Document General Module
+
+  // any attributes of the Raw Data Module that are present
+  // if (key == DCM_InstanceNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentDate) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDateTime) return OFTrue; // also in General Image Module
+  if (key == DCM_ContentLabel) return OFTrue;
+  if (key == DCM_ContentDescription) return OFTrue;
+  // if (key == DCM_ConceptNameCodeSequence) return OFTrue; // also in SR Document Content Module
+  // if (key == DCM_ImageLaterality) return OFTrue; // also in General Image Module
+  if (key == DCM_CreatorVersionUID) return OFTrue;
+  // if (key == DCM_ReferencedInstanceSequence) return OFTrue; // also in SR Document General Module
+
+  // if the Raw Data Module is present, we need to include all private tags into
+  // signature because the raw data as such is stored in private attributes.
+  if (((key.getGroup() & 1) == 1) && containsRawData_) return OFTrue;
+
+  // any attributes of the Enhanced CT Image Module that are present
+  // if (key == DCM_ImageType) return OFTrue; // also in General Image Module
+  if (key == DCM_MultienergyCTAcquisition) return OFTrue;
+  // if (key == DCM_AcquisitionNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDateTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDuration) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedRawDataSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedWaveformSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_SourceImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedPresentationStateSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_SamplesPerPixel) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PhotometricInterpretation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsAllocated) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsStored) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_HighBit) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_ContentQualification) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ImageComments) return OFTrue; // also in General Image Module
+  // if (key == DCM_BurnedInAnnotation) return OFTrue; // also in General Image Module
+  // if (key == DCM_RecognizableVisualFeatures) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompression) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionRatio) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionMethod) return OFTrue; // also in General Image Module
+  // if (key == DCM_PresentationLUTShape) return OFTrue; // also in General Image Module
+  // if (key == DCM_IconImageSequence) return OFTrue; // also in General Image Module
+  // if (key == DCM_IsocenterPosition) return OFTrue;  // also in Enhanced MR Image Module
+
+  // any attributes of the Enhanced XA/XRF Image Module that are present
+  // if (key == DCM_ImageType) return OFTrue; // also in General Image Module
+  if (key == DCM_PlanesInAcquisition) return OFTrue;
+  if (key == DCM_PlaneIdentification) return OFTrue;
+  // if (key == DCM_AcquisitionNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDateTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_BitsAllocated) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsStored) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_HighBit) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_SamplesPerPixel) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PixelRepresentation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PhotometricInterpretation) return OFTrue; // also in Image Pixel Module
+  if (key == DCM_AcquisitionProtocolName) return OFTrue;
+  if (key == DCM_AcquisitionProtocolDescription) return OFTrue;
+  if (key == DCM_ScanOptions) return OFTrue;
+  // if (key == DCM_ContentQualification) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_PatientOrientationCodeSequence) return OFTrue; // also in General Image Module
+  if (key == DCM_PatientGantryRelationshipCodeSequence) return OFTrue;
+  if (key == DCM_ExaminedBodyThickness) return OFTrue;
+  // if (key == DCM_BurnedInAnnotation) return OFTrue; // also in General Image Module
+  // if (key == DCM_RecognizableVisualFeatures) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompression) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionRatio) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionMethod) return OFTrue; // also in General Image Module
+  if (key == DCM_ReferencedOtherPlaneSequence) return OFTrue;
+  // if (key == DCM_ReferencedImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_SourceImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedInstanceSequence) return OFTrue; // also in SR Document General Module
+  // if (key == DCM_ImageComments) return OFTrue; // also in General Image Module
+  // if (key == DCM_QualityControlImage) return OFTrue; // also in General Image Module
+  // if (key == DCM_IconImageSequence) return OFTrue; // also in General Image Module
+  // if (key == DCM_PresentationLUTShape) return OFTrue; // also in General Image Module
+
+  // any attributes of the Segmentation Image Module that are present
+  // if (key == DCM_ImageType) return OFTrue; // also in General Image Module
+  if (key == DCM_ImageOrientationSlide) return OFTrue;
+  // if (key == DCM_SamplesPerPixel) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PhotometricInterpretation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PixelRepresentation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsAllocated) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsStored) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_HighBit) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_LossyImageCompression) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionRatio) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionMethod) return OFTrue; // also in General Image Module
+  if (key == DCM_SegmentationType) return OFTrue;
+  if (key == DCM_SegmentationFractionalType) return OFTrue;
+  if (key == DCM_MaximumFractionalValue) return OFTrue;
+  if (key == DCM_SegmentsOverlap) return OFTrue;
+  if (key == DCM_SegmentSequence) return OFTrue;
+
+  // any attributes of the Encapsulated Document Module that are present
+  // if (key == DCM_InstanceNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentDate) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDateTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_ImageLaterality) return OFTrue; // also in General Image Module
+  // if (key == DCM_BurnedInAnnotation) return OFTrue; // also in General Image Module
+  // if (key == DCM_RecognizableVisualFeatures) return OFTrue; // also in General Image Module
+  if (key == DCM_SourceInstanceSequence) return OFTrue;
+  if (key == DCM_DocumentTitle) return OFTrue;
+  // if (key == DCM_ConceptNameCodeSequence) return OFTrue; // also in SR Document Content Module
+  if (key == DCM_DocumentClassCodeSequence) return OFTrue;
+  // if (key == DCM_VerificationFlag) return OFTrue; // also in SR Document General Module
+  if (key == DCM_HL7InstanceIdentifier) return OFTrue;
+  // if (key == DCM_PredecessorDocumentsSequence) return OFTrue; // also in SR Document General Module
+  // if (key == DCM_IdenticalDocumentsSequence) return OFTrue; // also in SR Document General Module
+  if (key == DCM_MIMETypeOfEncapsulatedDocument) return OFTrue;
+  if (key == DCM_ListOfMIMETypes) return OFTrue;
+  if (key == DCM_EncapsulatedDocument) return OFTrue;
+  if (key == DCM_EncapsulatedDocumentLength) return OFTrue;
+  // if (key == DCM_ValueType) return OFTrue; // also in SR Document Content Module
+  // if (key == DCM_ContentSequence) return OFTrue; // also in SR Document Content Module
+  // if (key == DCM_ContinuityOfContent) return OFTrue; // also in SR Document Content Module
+  // if (key == DCM_ContentTemplateSequence) return OFTrue; // also in SR Document Content Module
+
+  // any attributes of the X-Ray 3D Image Module that are present
+  // if (key == DCM_ImageType) return OFTrue; // also in General Image Module
+  // if (key == DCM_BitsAllocated) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsStored) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_HighBit) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_SamplesPerPixel) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PhotometricInterpretation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_ContentQualification) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_BurnedInAnnotation) return OFTrue; // also in General Image Module
+  // if (key == DCM_RecognizableVisualFeatures) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompression) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionRatio) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionMethod) return OFTrue; // also in General Image Module
+  // if (key == DCM_ReferencedImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ImageComments) return OFTrue; // also in General Image Module
+  // if (key == DCM_QualityControlImage) return OFTrue; // also in General Image Module
+  // if (key == DCM_IconImageSequence) return OFTrue; // also in General Image Module
+  // if (key == DCM_PresentationLUTShape) return OFTrue; // also in General Image Module
+  if (key == DCM_SourceIrradiationEventSequence) return OFTrue;
+
+  // any attributes of the Enhanced PET Image Module that are present
+  // if (key == DCM_ImageType) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDateTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDuration) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedRawDataSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedWaveformSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_SourceImageEvidenceSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_SamplesPerPixel) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PhotometricInterpretation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsAllocated) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsStored) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_HighBit) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_ContentQualification) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ImageComments) return OFTrue; // also in General Image Module
+  // if (key == DCM_BurnedInAnnotation) return OFTrue; // also in General Image Module
+  // if (key == DCM_RecognizableVisualFeatures) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompression) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionRatio) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionMethod) return OFTrue; // also in General Image Module
+  // if (key == DCM_PresentationLUTShape) return OFTrue; // also in General Image Module
+  // if (key == DCM_IconImageSequence) return OFTrue; // also in General Image Module
+
+  // any attributes of the Enhanced US Image Module that are present
+  // if (key == DCM_ImageType) return OFTrue; // also in General Image Module
+  // if (key == DCM_SamplesPerPixel) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PhotometricInterpretation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsAllocated) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsStored) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_HighBit) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PixelRepresentation) return OFTrue; // also in Image Pixel Module
+  if (key == DCM_DimensionOrganizationType) return OFTrue;
+  // if (key == DCM_AcquisitionDateTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDuration) return OFTrue;  // also in Enhanced MR Image Module
+  if (key == DCM_PositionMeasuringDeviceUsed) return OFTrue;
+  // if (key == DCM_LossyImageCompression) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionRatio) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionMethod) return OFTrue; // also in General Image Module
+  // if (key == DCM_PresentationLUTShape) return OFTrue; // also in General Image Module
+  if (key == DCM_RescaleIntercept) return OFTrue;
+  if (key == DCM_RescaleSlope) return OFTrue;
+  if (key == DCM_SourceImageSequence) return OFTrue;
+  if (key == DCM_ReferencedImageSequence) return OFTrue;
+  // if (key == DCM_ReferencedRawDataSequence) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_ReferencedInstanceSequence) return OFTrue; // also in SR Document General Module
+  if (key == DCM_NumberOfStages) return OFTrue;
+  if (key == DCM_StageNumber) return OFTrue;
+  if (key == DCM_StageCodeSequence) return OFTrue;
+  if (key == DCM_EventTimerSequence) return OFTrue;
+  // if (key == DCM_BurnedInAnnotation) return OFTrue; // also in General Image Module
+  // if (key == DCM_RecognizableVisualFeatures) return OFTrue; // also in General Image Module
+  // if (key == DCM_IconImageSequence) return OFTrue; // also in General Image Module
+  if (key == DCM_TransducerData) return OFTrue;
+  if (key == DCM_TransducerGeometryCodeSequence) return OFTrue;
+  if (key == DCM_TransducerBeamSteeringCodeSequence) return OFTrue;
+  if (key == DCM_TransducerApplicationCodeSequence) return OFTrue;
+  if (key == DCM_ProcessingFunction) return OFTrue;
+  if (key == DCM_MechanicalIndex) return OFTrue;
+  if (key == DCM_BoneThermalIndex) return OFTrue;
+  if (key == DCM_CranialThermalIndex) return OFTrue;
+  if (key == DCM_SoftTissueThermalIndex) return OFTrue;
+  if (key == DCM_DepthsOfFocus) return OFTrue;
+  if (key == DCM_DepthOfScanField) return OFTrue;
+
+  // any attributes of the Surface Segmentation Module that are present
+  // if (key == DCM_InstanceNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentLabel) return OFTrue; // also in Raw Data Module
+  // if (key == DCM_ContentDescription) return OFTrue; // also in Raw Data Module
+  // if (key == DCM_ConceptNameCodeSequence) return OFTrue; // also in SR Document Content Module
+  if (key == DCM_AlternateContentDescriptionSequence) return OFTrue;
+  if (key == DCM_ContentCreatorName) return OFTrue;
+  if (key == DCM_ContentCreatorIdentificationCodeSequence) return OFTrue;
+  // if (key == DCM_ContentDate) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_SegmentSequence) return OFTrue; // also in Segmentation Image Module
+
+  // any attributes of the Surface Mesh Module that are present
+  if (key == DCM_NumberOfSurfaces) return OFTrue;
+  if (key == DCM_SurfaceSequence) return OFTrue;
+
+  // any attributes of the Structured Display Module that are present
+  // if (key == DCM_InstanceNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentLabel) return OFTrue; // also in Raw Data Module
+  // if (key == DCM_ContentDescription) return OFTrue; // also in Raw Data Module
+  // if (key == DCM_ConceptNameCodeSequence) return OFTrue; // also in SR Document Content Module
+  // if (key == DCM_AlternateContentDescriptionSequence) return OFTrue; // also in Surface Segmentation Module
+  // if (key == DCM_ContentCreatorName) return OFTrue; // also in Surface Segmentation Module
+  // if (key == DCM_ContentCreatorIdentificationCodeSequence) return OFTrue; // also in Surface Segmentation Module
+  if (key == DCM_PresentationCreationDate) return OFTrue;
+  if (key == DCM_PresentationCreationTime) return OFTrue;
+  if (key == DCM_NumberOfScreens) return OFTrue;
+  if (key == DCM_NominalScreenDefinitionSequence) return OFTrue;
+  // if (key == DCM_IconImageSequence) return OFTrue; // also in General Image Module
+  if (key == DCM_StructuredDisplayBackgroundCIELabValue) return OFTrue;
+  if (key == DCM_EmptyImageBoxCIELabValue) return OFTrue;
+  if (key == DCM_HangingProtocolName) return OFTrue;
+  if (key == DCM_HangingProtocolCreator) return OFTrue;
+
+  // any attributes of the Structured Display Annotation Module that are present
+  if (key == DCM_StructuredDisplayTextBoxSequence) return OFTrue;
+
+  // any attributes of the Structured Display Image Box Module that are present
+  if (key == DCM_StructuredDisplayImageBoxSequence) return OFTrue;
+  if (key == DCM_ImageBoxSynchronizationSequence) return OFTrue;
+
+  // any Attributes of the Implant Template Module that are present
+  // if (key == DCM_Manufacturer) return OFTrue; // also in General Equipment Module
+  if (key == DCM_FrameOfReferenceUID) return OFTrue;
+  if (key == DCM_ImplantName) return OFTrue;
+  if (key == DCM_ImplantSize) return OFTrue;
+  if (key == DCM_ImplantPartNumber) return OFTrue;
+  if (key == DCM_ImplantTemplateVersion) return OFTrue;
+  if (key == DCM_ReplacedImplantTemplateSequence) return OFTrue;
+  if (key == DCM_ImplantType) return OFTrue;
+  if (key == DCM_OriginalImplantTemplateSequence) return OFTrue;
+  if (key == DCM_DerivationImplantTemplateSequence) return OFTrue;
+  if (key == DCM_EffectiveDateTime) return OFTrue;
+  if (key == DCM_ImplantTargetAnatomySequence) return OFTrue;
+  if (key == DCM_NotificationFromManufacturerSequence) return OFTrue;
+  if (key == DCM_InformationFromManufacturerSequence) return OFTrue;
+  if (key == DCM_ImplantRegulatoryDisapprovalCodeSequence) return OFTrue;
+  if (key == DCM_OverallTemplateSpatialTolerance) return OFTrue;
+  if (key == DCM_MaterialsCodeSequence) return OFTrue;
+  if (key == DCM_CoatingMaterialsCodeSequence) return OFTrue;
+  if (key == DCM_ImplantTypeCodeSequence) return OFTrue;
+  if (key == DCM_FixationMethodCodeSequence) return OFTrue;
+
+  // any Attributes of the Implant Assembly Template Module that are present
+  // if (key == DCM_EffectiveDateTime) return OFTrue; // also in Implant Template Module
+  if (key == DCM_ImplantAssemblyTemplateName) return OFTrue;
+  if (key == DCM_ImplantAssemblyTemplateIssuer) return OFTrue;
+  if (key == DCM_ImplantAssemblyTemplateVersion) return OFTrue;
+  if (key == DCM_ReplacedImplantAssemblyTemplateSequence) return OFTrue;
+  if (key == DCM_ImplantAssemblyTemplateType) return OFTrue;
+  if (key == DCM_OriginalImplantAssemblyTemplateSequence) return OFTrue;
+  if (key == DCM_DerivationImplantAssemblyTemplateSequence) return OFTrue;
+  if (key == DCM_ImplantAssemblyTemplateTargetAnatomySequence) return OFTrue;
+  if (key == DCM_ProcedureTypeCodeSequence) return OFTrue;
+  if (key == DCM_SurgicalTechnique) return OFTrue;
+  // if (key == DCM_MIMETypeOfEncapsulatedDocument) return OFTrue; // also in Encapsulated Document Module
+  // if (key == DCM_EncapsulatedDocument) return OFTrue; // also in Encapsulated Document Module
+  if (key == DCM_ComponentTypesSequence) return OFTrue;
+  if (key == DCM_ComponentAssemblySequence) return OFTrue;
+
+  // any Attributes of the Implant Template Group Module that are present
+  // if (key == DCM_EffectiveDateTime) return OFTrue; // also in Implant Template Module
+  if (key == DCM_ImplantTemplateGroupName) return OFTrue;
+  if (key == DCM_ImplantTemplateGroupDescription) return OFTrue;
+  if (key == DCM_ImplantTemplateGroupIssuer) return OFTrue;
+  if (key == DCM_ImplantTemplateGroupVersion) return OFTrue;
+  if (key == DCM_ReplacedImplantTemplateGroupSequence) return OFTrue;
+  if (key == DCM_ImplantTemplateGroupTargetAnatomySequence) return OFTrue;
+  if (key == DCM_ImplantTemplateGroupMembersSequence) return OFTrue;
+  if (key == DCM_ImplantTemplateGroupVariationDimensionSequence) return OFTrue;
+
+  // any attributes of the Point Cloud Module that are present
+  if (key == DCM_SurfacePointsSequence) return OFTrue;
+  if (key == DCM_SurfacePointPresentationValueData) return OFTrue;
+  if (key == DCM_SurfacePointColorCIELabValueData) return OFTrue;
+
+  // any attributes of the Enhanced Mammography Image Module that are present
+  if (key == DCM_PositionerMotion) return OFTrue;
+  if (key == DCM_PositionerType) return OFTrue;
+  // if (key == DCM_ContentQualification) return OFTrue;  // also in Enhanced MR Image Module
+  // if (key == DCM_AcquisitionDateTime) return OFTrue; // also in General Image Module
+  // if (key == DCM_AcquisitionDuration) return OFTrue;  // also in Enhanced MR Image Module
+  if (key == DCM_KVP) return OFTrue;
+  if (key == DCM_XRayTubeCurrentInmA) return OFTrue;
+  if (key == DCM_ExposureTimeInms) return OFTrue;
+  if (key == DCM_ExposureInmAs) return OFTrue;
+  if (key == DCM_FocalSpots) return OFTrue;
+  if (key == DCM_AnodeTargetMaterial) return OFTrue;
+  if (key == DCM_BodyPartThickness) return OFTrue;
+  if (key == DCM_CompressionForce) return OFTrue;
+  if (key == DCM_CompressionPressure) return OFTrue;
+  if (key == DCM_CompressionContactArea) return OFTrue;
+  if (key == DCM_PaddleDescription) return OFTrue;
+  if (key == DCM_ExposureControlMode) return OFTrue;
+  if (key == DCM_ExposureControlModeDescription) return OFTrue;
+  if (key == DCM_PatientOrientation) return OFTrue;
+  // if (key == DCM_ImageComments) return OFTrue; // also in General Image Module
+  // if (key == DCM_SamplesPerPixel) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PhotometricInterpretation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsAllocated) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_BitsStored) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_HighBit) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_PixelRepresentation) return OFTrue; // also in Image Pixel Module
+  // if (key == DCM_QualityControlImage) return OFTrue; // also in General Image Module
+  // if (key == DCM_BurnedInAnnotation) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompression) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionRatio) return OFTrue; // also in General Image Module
+  // if (key == DCM_LossyImageCompressionMethod) return OFTrue; // also in General Image Module
+  if (key == DCM_OrganDose) return OFTrue;
+  if (key == DCM_EntranceDoseInmGy) return OFTrue;
+  if (key == DCM_EntranceDoseDerivation) return OFTrue;
+  if (key == DCM_TypeOfDetectorMotion) return OFTrue;
+  // if (key == DCM_IconImageSequence) return OFTrue; // also in General Image Module
+  // if (key == DCM_PresentationLUTShape) return OFTrue; // also in General Image Module
+
+  // any attributes of the Tractography Results Module that are present
+  // if (key == DCM_InstanceNumber) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentLabel) return OFTrue; // also in Raw Data Module
+  // if (key == DCM_ContentDescription) return OFTrue; // also in Raw Data Module
+  // if (key == DCM_ConceptNameCodeSequence) return OFTrue; // also in SR Document Content Module
+  // if (key == DCM_AlternateContentDescriptionSequence) return OFTrue; // also in Surface Segmentation Module
+  // if (key == DCM_ContentCreatorName) return OFTrue; // also in Surface Segmentation Module
+  // if (key == DCM_ContentCreatorIdentificationCodeSequence) return OFTrue; // also in Surface Segmentation Module
+  // if (key == DCM_ContentDate) return OFTrue; // also in General Image Module
+  // if (key == DCM_ContentTime) return OFTrue; // also in General Image Module
+  if (key == DCM_TrackSetSequence) return OFTrue;
+  // if (key == DCM_ReferencedInstanceSequence) return OFTrue; // also in SR Document General Module
+
+  // any attributes of the Volumetric Graphic Annotation Module that are present
+  if (key == DCM_VolumetricAnnotationSequence) return OFTrue;
+  if (key == DCM_VolumetricPresentationInputAnnotationSequence) return OFTrue;
 
   return OFFalse;
 }
 
+
+OFBool SiCreatorProfile::checkRequiredAttributeList(DcmAttributeTag& tagList) const
+{
+  OFBool result =
+    containsTag(tagList, DCM_SOPClassUID) &&
+    containsTag(tagList, DCM_StudyInstanceUID) &&
+    containsTag(tagList, DCM_SeriesInstanceUID) &&
+    containsTag(tagList, DCM_SOPInstanceUID);
+
+  return result;
+}
+
+
+OFCondition SiCreatorProfile::inspectSignatureDataset(DcmItem &item)
+{
+  DcmElement *delem = NULL;
+  if (item.findAndGetElement(DCM_CreatorVersionUID, delem).good())
+  {
+    // The CreatorVersionUID attribute is present in the dataset or item.
+    // Since this attribute only occurs in the Raw Data Module, this means that
+    // the Raw Data Module is present.
+    containsRawData_ = OFTrue;
+  }
+  else
+  {
+    containsRawData_ = OFFalse;
+  }
+  return EC_Normal;
+}
+
+OFBool SiCreatorProfile::mainDatasetRequired() const
+{
+  return OFTrue;
+}
+
 #else /* WITH_OPENSSL */
 
 int sicreapr_cc_dummy_to_keep_linker_from_moaning = 0;
diff --git a/dcmsign/libsrc/siecdsa.cc b/dcmsign/libsrc/siecdsa.cc
new file mode 100644 (file)
index 0000000..f1b3502
--- /dev/null
@@ -0,0 +1,188 @@
+/*
+ *
+ *  Copyright (C) 1998-2019, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmsign
+ *
+ *  Author: Norbert Loxen, Marco Eichelberg
+ *
+ *  Purpose:
+ *    classes: SiECDSA
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#ifdef WITH_OPENSSL
+
+#include "dcmtk/dcmsign/siecdsa.h"
+#include "dcmtk/dcmsign/sicert.h"
+#include "dcmtk/dcmsign/siprivat.h"
+
+BEGIN_EXTERN_C
+#include <openssl/err.h>
+#include <openssl/evp.h>
+#ifndef OPENSSL_NO_EC
+#include <openssl/ec.h>
+#include <openssl/ecdsa.h>
+#endif
+END_EXTERN_C
+
+SiECDSA::SiECDSA(EC_KEY *key)
+: ecdsa(key)
+{
+}
+
+#ifndef OPENSSL_NO_EC
+
+SiECDSA::~SiECDSA()
+{
+  if (ecdsa) EC_KEY_free(ecdsa);
+}
+
+
+OFCondition SiECDSA::sign(
+    const unsigned char *inputHash,
+    unsigned long inputHashSize,
+    E_MACType inputHashAlgorithm,
+    unsigned char *outputSignature,
+    unsigned long &outputSignatureSize)
+{
+    if (ecdsa==NULL) return SI_EC_InitializationFailed;
+    int openSSLmac = 0;
+    switch (inputHashAlgorithm)
+    {
+      case EMT_SHA1:
+        openSSLmac = NID_sha1;
+        break;
+      case EMT_RIPEMD160:
+        openSSLmac = NID_ripemd160;
+        break;
+      case EMT_MD5:
+        openSSLmac = NID_md5;
+        break;
+      case EMT_SHA256:
+        openSSLmac = NID_sha256;
+        break;
+      case EMT_SHA384:
+        openSSLmac = NID_sha384;
+        break;
+      case EMT_SHA512:
+        openSSLmac = NID_sha512;
+        break;
+    }
+    unsigned int sigLen = 0;
+    int error = ECDSA_sign(openSSLmac, inputHash, (unsigned int)inputHashSize, outputSignature, &sigLen, ecdsa);
+    outputSignatureSize = sigLen;
+    if (error < 0) return SI_EC_OpenSSLFailure;
+    return EC_Normal;
+}
+
+
+OFCondition SiECDSA::verify(
+    const unsigned char *inputHash,
+    unsigned long inputHashSize,
+    E_MACType inputHashAlgorithm,
+    const unsigned char *inputSignature,
+    unsigned long inputSignatureSize,
+    OFBool &verified)
+{
+    verified = OFFalse;
+    if (ecdsa==NULL) return SI_EC_InitializationFailed;
+    int openSSLmac = 0;
+    switch (inputHashAlgorithm)
+    {
+      case EMT_SHA1:
+        openSSLmac = NID_sha1;
+        break;
+      case EMT_RIPEMD160:
+        openSSLmac = NID_ripemd160;
+        break;
+      case EMT_MD5:
+        openSSLmac = NID_md5;
+        break;
+      case EMT_SHA256:
+        openSSLmac = NID_sha256;
+        break;
+      case EMT_SHA384:
+        openSSLmac = NID_sha384;
+        break;
+      case EMT_SHA512:
+        openSSLmac = NID_sha512;
+        break;
+    }
+
+    // we have to cast away const on inputSignature yet because of OpenSSL limitations
+    int error = ECDSA_verify(openSSLmac, inputHash, (unsigned int)inputHashSize, (unsigned char *)inputSignature, (unsigned int)inputSignatureSize, ecdsa);
+
+    if (error < 0)
+    {
+      const char *err = ERR_reason_error_string(ERR_peek_error());
+      if (err) DCMSIGN_ERROR("OpenSSL error: " << err);
+      return SI_EC_OpenSSLFailure;
+    }
+    else if (error > 0) verified = OFTrue;
+
+    return EC_Normal;
+}
+
+
+unsigned long SiECDSA::getSize() const
+{
+  if (ecdsa == NULL) return 0;
+  return ECDSA_size(ecdsa);
+}
+
+#else /* OPENSSL_NO_EC */
+
+SiECDSA::~SiECDSA()
+{
+}
+
+OFCondition SiECDSA::sign(
+    const unsigned char * /* inputHash */,
+    unsigned long /* inputHashSize */,
+    E_MACType /* inputHashAlgorithm */,
+    unsigned char * /* outputSignature */,
+    unsigned long& /* outputSignatureSize */)
+{
+    return SI_EC_EllipticCurveNotSupported;
+}
+
+OFCondition SiECDSA::verify(
+    const unsigned char * /* inputHash */,
+    unsigned long /* inputHashSize */,
+    E_MACType /* inputHashAlgorithm */,
+    const unsigned char * /* inputSignature */,
+    unsigned long /* inputSignatureSize */,
+    OFBool& /* verified */)
+{
+    return SI_EC_EllipticCurveNotSupported;
+}
+
+unsigned long SiECDSA::getSize() const
+{
+  return 0;
+}
+
+#endif /* OPENSSL_NO_EC */
+
+E_KeyType SiECDSA::keyType() const
+{
+  return EKT_EC;
+}
+
+#else /* WITH_OPENSSL */
+
+int SiECDSA_cc_dummy_to_keep_linker_from_moaning = 0;
+
+#endif
index cdd91a60f54b1437e2dcf204fdd6021b5591ca83..2f2474a2e30ce82c2c215910edb2ffa7303ef7f4 100644 (file)
@@ -189,15 +189,65 @@ OFCondition SiMACConstructor::encodeDataset(
           result = tagListOut.putTagVal(element->getTag(), tagListOut.getVM());
         }
       }
+      else
+      {
+        // the element is unsignable, but either the user or the active
+        // signature profile have requested its inclusion in the signature.
+        if (tagListIn)
+        {
+          // print a warning
+          DcmTag tag(element->getTag()); // we need to create a temporary copy of the tag
+          DCMSIGN_INFO("List of attributes to be signed contains unsignable element " << tag << " " << tag.getTagName() );
+          result = SI_EC_AttributeNotSignable;
+        }
+      }
     }
   }
 
   /* done, flush stream buffer */
-  result = flushBuffer(mac);
+  if (result.good()) result = flushBuffer(mac);
   item.transferEnd();
   return result;
 }
 
+
+OFCondition SiMACConstructor::encodeDatasetForVerification(
+  DcmItem& item,
+  SiMAC& mac,
+  E_TransferSyntax oxfer,
+  DcmAttributeTag *tagListIn)
+{
+  if (! item.canWriteXfer(oxfer, EXS_Unknown)) return SI_EC_WrongTransferSyntax;
+
+  OFCondition result = EC_Normal;
+  item.transferInit();
+  unsigned long numElements = item.card();
+  DcmElement *element;
+  for (unsigned long i=0; i < numElements; i++)
+  {
+    element = item.getElement(i);
+    if (result.good() && (inTagList(element, tagListIn)))
+    {
+      if (element->isSignable())
+      {
+        // element is signable, we should encode it
+        result = encodeElement(element, mac, oxfer);
+      }
+      else
+      {
+        // print a warning
+        DcmTag tag(element->getTag()); // we need to create a temporary copy of the tag
+        DCMSIGN_INFO("  Signature contains unsignable element " << tag << " " << tag.getTagName() );
+        result = SI_EC_VerificationFailed_AttributeNotSignable;
+      }
+    }
+  }
+
+  /* done, flush stream buffer */
+  if (result.good()) result = flushBuffer(mac);
+  item.transferEnd();
+  return result;
+}
 #else /* WITH_OPENSSL */
 
 int simaccon_cc_dummy_to_keep_linker_from_moaning = 0;
index 43d09c8b0d76aea05f4c70018b5fb440663eb152..ac525ad95107d1a39c4c75b3dd3c290d5e29f677 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2010, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -37,11 +37,16 @@ OFBool SiNullProfile::isAllowableAlgorithmType(E_KeyType keyType) const
   return OFTrue;
 }
 
-OFBool SiNullProfile::attributeRequired(const DcmTagKey& /* key */) const
+OFBool SiNullProfile::attributeRequiredIfPresent(const DcmTagKey& /* key */) const
 {
   return OFFalse;
 }
 
+OFBool SiNullProfile::checkRequiredAttributeList(DcmAttributeTag& /* tagList */) const
+{
+  return OFTrue;
+}
+
 OFBool SiNullProfile::attributeForbidden(const DcmTagKey& /* key */) const
 {
   return OFFalse;
@@ -53,6 +58,17 @@ OFBool SiNullProfile::isAllowableTransferSyntax(E_TransferSyntax xfer) const
   return OFTrue;
 }
 
+OFCondition SiNullProfile::inspectSignatureDataset(DcmItem & /* item */)
+{
+  return EC_Normal;
+}
+
+OFBool SiNullProfile::mainDatasetRequired() const
+{
+  return OFFalse;
+}
+
+
 #else /* WITH_OPENSSL */
 
 int sinullpr_cc_dummy_to_keep_linker_from_moaning = 0;
index 6e0127949692e90f56a471277345e624630d4578..d6bff55f840a79d1940c419580388e508c36d1b9 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -27,6 +27,7 @@
 #include "dcmtk/dcmsign/siprivat.h"
 #include "dcmtk/dcmsign/sirsa.h"
 #include "dcmtk/dcmsign/sidsa.h"
+#include "dcmtk/dcmsign/siecdsa.h"
 #include "dcmtk/dcmsign/sicert.h"
 
 #define INCLUDE_CSTRING
@@ -94,7 +95,7 @@ void SiPrivateKey::setPrivateKeyPasswdFromConsole()
 
 OFCondition SiPrivateKey::loadPrivateKey(const char *filename, int filetype)
 {
-  OFCondition result = SI_EC_CannotRead;  
+  OFCondition result = SI_EC_CannotRead;
   if (pkey) EVP_PKEY_free(pkey);
   pkey = NULL;
   if (filename)
@@ -128,7 +129,7 @@ E_KeyType SiPrivateKey::getKeyType() const
   E_KeyType result = EKT_none;
   if (pkey)
   {
-    switch(EVP_PKEY_id(pkey))
+    switch(EVP_PKEY_type(EVP_PKEY_id(pkey)))
     {
       case EVP_PKEY_RSA:
         result = EKT_RSA;
@@ -139,6 +140,9 @@ E_KeyType SiPrivateKey::getKeyType() const
       case EVP_PKEY_DH:
         result = EKT_DH;
         break;
+      case EVP_PKEY_EC:
+        result = EKT_EC;
+        break;
       default:
         /* nothing */
         break;
@@ -152,7 +156,7 @@ SiAlgorithm *SiPrivateKey::createAlgorithmForPrivateKey()
 {
   if (pkey)
   {
-    switch(EVP_PKEY_id(pkey))
+    switch(EVP_PKEY_type(EVP_PKEY_id(pkey)))
     {
       case EVP_PKEY_RSA:
         return new SiRSA(EVP_PKEY_get1_RSA(pkey));
@@ -160,12 +164,19 @@ SiAlgorithm *SiPrivateKey::createAlgorithmForPrivateKey()
       case EVP_PKEY_DSA:
         return new SiDSA(EVP_PKEY_get1_DSA(pkey));
         /* break; */
+      case EVP_PKEY_EC:
+#ifdef OPENSSL_NO_EC
+        return new SiECDSA(NULL);
+#else
+        return new SiECDSA(EVP_PKEY_get1_EC_KEY(pkey));
+#endif
+        /* break; */
       case EVP_PKEY_DH:
       default:
         /* nothing */
         break;
     }
-  }    
+  }
   return NULL;
 }
 
diff --git a/dcmsign/libsrc/sipurpos.cc b/dcmsign/libsrc/sipurpos.cc
new file mode 100644 (file)
index 0000000..2afcf70
--- /dev/null
@@ -0,0 +1,159 @@
+/*
+ *
+ *  Copyright (C) 2019, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmsign
+ *
+ *  Author: Marco Eichelberg
+ *
+ *  Purpose:
+ *    classes: SiSignaturePurpose
+ *
+ */
+#include "dcmtk/config/osconfig.h"
+
+#ifdef WITH_OPENSSL
+
+#include "dcmtk/dcmsign/sipurpos.h"
+#include "dcmtk/dcmsign/sitypes.h"
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmdata/dcitem.h"
+#include "dcmtk/ofstd/ofstream.h"
+
+// code value constants
+static const char *purposeCodeValue[] =
+{
+    NULL,
+    "1",   "2",   "3",   "4",   "5",  "6",
+    "7",   "8",   "9",  "10",  "11", "12",
+    "13",  "14", "15",  "16", "17",  "18"
+};
+
+static const size_t purposeCodeValueEntries = sizeof(purposeCodeValue) / sizeof(const char *);
+
+// code meaning constants
+static const char *purposeCodeMeaning[] =
+{
+    NULL,
+    "Author's Signature",
+    "Coauthor's Signature",
+    "Co-participant's Signature",
+    "Transcriptionist/Recorder Signature",
+    "Verification Signature",
+    "Validation Signature",
+    "Consent Signature",
+    "Signature Witness Signature",
+    "Event Witness Signature",
+    "Identity Witness Signature",
+    "Consent Witness Signature",
+    "Interpreter Signature",
+    "Review Signature",
+    "Source Signature",
+    "Addendum Signature",
+    "Modification Signature",
+    "Administrative (Error/Edit) Signature",
+    "Timestamp Signature"
+};
+
+static const size_t purposeCodeMeaningEntries = sizeof(purposeCodeMeaning) / sizeof(const char *);
+
+const char *SiSignaturePurpose::getCodeValue(E_SignaturePurposeType purpose)
+{
+    size_t idx = OFstatic_cast(size_t, purpose); // cast the enum to size_t
+    if ((idx > 0) && (idx < purposeCodeValueEntries)) return purposeCodeValue[idx];
+    return NULL;
+}
+
+const char *SiSignaturePurpose::getCodeMeaning(E_SignaturePurposeType purpose)
+{
+    size_t idx = OFstatic_cast(size_t, purpose); // cast the enum to size_t
+    if ((idx > 0) && (idx < purposeCodeMeaningEntries)) return purposeCodeMeaning[idx];
+    return NULL;
+}
+
+const char *SiSignaturePurpose::getCodingSchemeDesignator(E_SignaturePurposeType /* purpose */)
+{
+  return "ASTM-sigpurpose";
+}
+
+OFCondition SiSignaturePurpose::insertDigitalSignaturePurposeCodeSQ(DcmItem& seqItem, E_SignaturePurposeType sigPurpose)
+{
+    if (sigPurpose == ESP_none) return EC_Normal; // no signature purpose defined
+
+    OFCondition result = EC_Normal;
+    const char *codeValue = getCodeValue(sigPurpose);
+    const char *codeMeaning = getCodeMeaning(sigPurpose);
+    const char *codingSchemeDesignator = getCodingSchemeDesignator(sigPurpose);
+
+    if (codeValue && codeMeaning && codingSchemeDesignator)
+    {
+        DcmItem *ditem = NULL;
+        result = seqItem.findOrCreateSequenceItem(DCM_DigitalSignaturePurposeCodeSequence, ditem);
+        if (ditem)
+        {
+          if (result.good()) result = ditem->putAndInsertString(DCM_CodingSchemeDesignator, codingSchemeDesignator);
+          if (result.good()) result = ditem->putAndInsertString(DCM_CodeValue, codeValue);
+          if (result.good()) result = ditem->putAndInsertString(DCM_CodeMeaning, codeMeaning);
+        }
+    }
+    else result = EC_IllegalCall; // we were called with an undefined signature purpose
+    return result;
+}
+
+SiSignaturePurpose::E_SignaturePurposeType SiSignaturePurpose::determineOverridePurpose(E_SignaturePurposeType currentPurpose, E_SignaturePurposeType overridePurpose)
+{
+    if (overridePurpose != ESP_none)
+    {
+        if ((currentPurpose != ESP_none) && (currentPurpose != overridePurpose))
+        {
+            // we have a conflict between user selection and profile requirements
+            DCMSIGN_WARN("Signature profile requires purpose code " << OFstatic_cast(int, overridePurpose) << ", ignoring user selection " << OFstatic_cast(int, currentPurpose) << ".");
+        }
+        // the signature profile overrides the user's selection
+        currentPurpose = overridePurpose;
+    }
+    return currentPurpose;
+}
+
+SiSignaturePurpose::E_SignaturePurposeType SiSignaturePurpose::lookup(size_t num)
+{
+    if (num < purposeCodeValueEntries) return OFstatic_cast(E_SignaturePurposeType, num); else return ESP_none;
+}
+
+void SiSignaturePurpose::printSignatureCodes(STD_NAMESPACE ostream& out)
+{
+    out << "\nDigital Signature Purpose Codes:\n"
+           "   1: Author's Signature\n"
+           "   2: Coauthor's Signature\n"
+           "   3: Co-participant's Signature\n"
+           "   4: Transcriptionist/Recorder Signature\n"
+           "   5: Verification Signature\n"
+           "   6: Validation Signature\n"
+           "   7: Consent Signature\n"
+           "   8: Signature Witness Signature\n"
+           "   9: Event Witness Signature\n"
+           "  10: Identity Witness Signature\n"
+           "  11: Consent Witness Signature\n"
+           "  12: Interpreter Signature\n"
+           "  13: Review Signature\n"
+           "  14: Source Signature\n"
+           "  15: Addendum Signature\n"
+           "  16: Modification Signature\n"
+           "  17: Administrative (Error/Edit) Signature\n"
+           "  18: Timestamp Signature\n"
+        << OFendl;
+    return;
+}
+
+#else /* WITH_OPENSSL */
+int sipurpos_cc_dummy_to_keep_linker_from_moaning = 0;
+#endif
index ca2d3d8de25abb63e2209c7ad63197316062feec..03e142561a0f444643f3bff45d9db90f3fd0171b 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2010, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -30,6 +30,8 @@
 #include "dcmtk/dcmsign/simac.h"     /* for SiMAC */
 #include "dcmtk/dcmsign/sialgo.h"    /* for SiAlgorithm */
 
+#include "dcmtk/dcmdata/dcdeftag.h"
+
 OFBool SiSecurityProfile::isAllowableMAC(const SiMAC& mac) const
 {
   return isAllowableMACType(mac.macType());
@@ -44,32 +46,65 @@ OFBool SiSecurityProfile::isAllowableAlgorithm(const SiAlgorithm& algo) const
 
 OFCondition SiSecurityProfile::updateAttributeList(DcmItem &item, DcmAttributeTag& tagList)
 {
-  OFCondition result = EC_Normal;
   unsigned long card = item.card();
   if (card == 0)
   {
     // nothing to sign
     tagList.clear();
-    return result;
+    return SI_EC_DatasetEmpty;
   }
+
+  OFCondition result = EC_Normal;
   unsigned long maxArray = 2*card;
   Uint16 *array = new Uint16[maxArray];
   if (array == NULL) return EC_MemoryExhausted;
-  unsigned long i=0;  
+  unsigned long i=0;
   for (i=0; i<maxArray; i++) array[i]=0;
   DcmElement *elem = NULL;
 
-  // for all elements in the dataset, check if we want to have them in the list  
+  // for all elements in the dataset, check if we want to have them in the list
   for (i=0; i<card; i++)
   {
     elem = item.getElement(i);
-    const DcmTagKey& key = elem->getTag();
-    if (key.isSignableTag())
+    const DcmTag& key = elem->getTag();
+
+    if (containsTag(tagList, key))
+    {
+      // tag is already in the list of elements to be signed. Check if this is permitted
+      if (elem->isSignable() && !attributeForbidden(key))
+      {
+        array[2*i] = key.getGroup();
+        array[2*i+1] = key.getElement();
+      }
+      else if (attributeForbidden(key))
+      {
+        DcmTag tag(key);
+        DCMSIGN_INFO("List of attributes to be signed contains element forbidden by signature profile: " << tag << " " << tag.getTagName() );
+        result = SI_EC_AttributeNotSignable;
+      }
+      else
+      {
+        DcmTag tag(key);
+        DCMSIGN_INFO("List of attributes to be signed contains unsignable element " << tag << " " << tag.getTagName() );
+        result = SI_EC_AttributeNotSignable;
+      }
+    }
+    else
     {
-      if ((attributeRequired(key))||((containsTag(tagList, key))&&(! attributeForbidden(key))))
+      // tag is not in the list of elements to be signed. Check if we should include it
+      if (attributeRequiredIfPresent(key))
       {
-       array[2*i] = key.getGroup();
-       array[2*i+1] = key.getElement();
+        if (elem->isSignable())
+        {
+          array[2*i] = key.getGroup();
+          array[2*i+1] = key.getElement();
+        }
+        else
+        {
+          DcmTag tag(key);
+          DCMSIGN_INFO("List of attributes to be signed according to signature profile contains unsignable element " << tag << " " << tag.getTagName() );
+          result = SI_EC_AttributeNotSignable;
+        }
       }
     }
   }
@@ -85,19 +120,108 @@ OFCondition SiSecurityProfile::updateAttributeList(DcmItem &item, DcmAttributeTa
       array [j++] = array[i++];
     } else i += 2;
   }
-  
+
   // now copy nonzero entries from array to tagList
   tagList.clear();
-  if (j > 0)
+  if (j > 0 && result.good())
   {
     result = tagList.putUint16Array(array, j>>1);
   }
+  delete[] array;
+
+  if (result.good())
+  {
+    if (!checkRequiredAttributeList(tagList))
+    {
+      result = SI_EC_RequiredAttributeMissing;
+    }
+  }
+
+  return result;
+}
+
+
+OFCondition SiSecurityProfile::createAttributeList(DcmItem &item, DcmAttributeTag& tagList)
+{
+  unsigned long card = item.card();
+  if (card == 0) return SI_EC_DatasetEmpty;
+
+  OFCondition result = EC_Normal;
+  unsigned long maxArray = 2*card;
+  Uint16 *array = new Uint16[maxArray];
+  if (array == NULL) return EC_MemoryExhausted;
+  unsigned long i=0;
+  for (i=0; i<maxArray; i++) array[i]=0;
+  DcmElement *elem = NULL;
+
+  // for all elements in the dataset, check if we want to have them in the list
+  for (i=0; i<card; i++)
+  {
+    elem = item.getElement(i);
+    const DcmTag& key = elem->getTag();
+
+    if (attributeRequiredIfPresent(key))
+    {
+      // attribute is present and required
+      if (elem->isSignable())
+      {
+        array[2*i] = key.getGroup();
+        array[2*i+1] = key.getElement();
+      }
+      else
+      {
+        DcmTag tag(key);
+        DCMSIGN_INFO("List of attributes to be signed according to signature profile contains unsignable element " << tag << " " << tag.getTagName() );
+        result = SI_EC_AttributeNotSignable;
+      }
+    }
+    else
+    {
+      // attribute is not required. Include it if permitted, ignore it otherwise.
+      if (elem->isSignable() && !attributeForbidden(key))
+      {
+        array[2*i] = key.getGroup();
+        array[2*i+1] = key.getElement();
+      }
+    }
+  }
+
+  // pack array
+  unsigned long j=0;
+  i = 0;
+  while (i < maxArray)
+  {
+    if (array[i] > 0)
+    {
+      array [j++] = array[i++];
+      array [j++] = array[i++];
+    } else i += 2;
+  }
+
+  // now copy nonzero entries from array to tagList
+  tagList.clear();
+  if (j > 0 && result.good())
+  {
+    result = tagList.putUint16Array(array, j>>1);
+  }
+  delete[] array;
+
+  if (result.good())
+  {
+    if (!checkRequiredAttributeList(tagList))
+    {
+      result = SI_EC_RequiredAttributeMissing;
+    }
+  }
+
   return result;
 }
 
 
 OFBool SiSecurityProfile::checkAttributeList(DcmItem &item, DcmAttributeTag& tagList)
 {
+  // first check if all attributes that must be signed if present
+  // are included in the signature, if present
   DcmElement *elem = NULL;
   unsigned long card = item.card();
   for (unsigned long i=0; i<card; i++)
@@ -110,13 +234,16 @@ OFBool SiSecurityProfile::checkAttributeList(DcmItem &item, DcmAttributeTag& tag
       {
         if (attributeForbidden(key)) return OFFalse; // attribute is signed but forbidden
       } else {
-        if (attributeRequired(key)) return OFFalse;  // attribute is required but unsigned
+        if (attributeRequiredIfPresent(key)) return OFFalse;  // attribute is required but unsigned
       }
     } else {
       if (containsTag(tagList, key)) return OFFalse; // unsignable tag contained in list
     }
   }
-  return OFTrue;
+
+  // finally check if all attributes that must be signed unconditionally
+  // are included in the signature.
+  return checkRequiredAttributeList(tagList);
 }
 
 
@@ -131,6 +258,11 @@ OFBool SiSecurityProfile::containsTag(DcmAttributeTag& tagList, const DcmTagKey&
   return OFFalse;
 }
 
+SiSignaturePurpose::E_SignaturePurposeType SiSecurityProfile::getOverrideSignaturePurpose() const
+{
+  return SiSignaturePurpose::ESP_none;
+}
+
 
 #else /* WITH_OPENSSL */
 
diff --git a/dcmsign/libsrc/sisrpr.cc b/dcmsign/libsrc/sisrpr.cc
new file mode 100644 (file)
index 0000000..6bb59c2
--- /dev/null
@@ -0,0 +1,172 @@
+/*
+ *
+ *  Copyright (C) 2019, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmsign
+ *
+ *  Author: Marco Eichelberg
+ *
+ *  Purpose:
+ *    classes: SiStructuredReportingProfile
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#ifdef WITH_OPENSSL
+
+#include "dcmtk/dcmsign/sisrpr.h"
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmdata/dcitem.h"
+#include "dcmtk/dcmsign/sitypes.h"
+
+OFBool SiStructuredReportingProfile::attributeRequiredIfPresent(const DcmTagKey& key) const
+{
+
+  // the SOP Class UID
+  if (key == DCM_SOPClassUID) return OFTrue;
+
+  // the Study and Series Instance UIDs
+  if (key == DCM_StudyInstanceUID) return OFTrue;
+  if (key == DCM_SeriesInstanceUID) return OFTrue;
+
+  // all attributes of the General Equipment Module that are present
+  if (key == DCM_Manufacturer) return OFTrue;
+  if (key == DCM_InstitutionName) return OFTrue;
+  if (key == DCM_InstitutionAddress) return OFTrue;
+  if (key == DCM_StationName) return OFTrue;
+  if (key == DCM_InstitutionalDepartmentName) return OFTrue;
+  if (key == DCM_InstitutionalDepartmentTypeCodeSequence) return OFTrue;
+  if (key == DCM_ManufacturerModelName) return OFTrue;
+  if (key == DCM_DeviceSerialNumber) return OFTrue;
+  if (key == DCM_SoftwareVersions) return OFTrue;
+  if (key == DCM_GantryID) return OFTrue;
+  if (key == DCM_UDISequence) return OFTrue;
+  if (key == DCM_DeviceUID) return OFTrue;
+  if (key == DCM_SpatialResolution) return OFTrue;
+  if (key == DCM_DateOfLastCalibration) return OFTrue;
+  if (key == DCM_TimeOfLastCalibration) return OFTrue;
+  if (key == DCM_PixelPaddingValue) return OFTrue;
+
+  // the Current Requested Procedure Evidence Sequence
+  if (key == DCM_CurrentRequestedProcedureEvidenceSequence) return OFTrue;
+
+  // the Pertinent Other Evidence Sequence
+  if (key == DCM_PertinentOtherEvidenceSequence) return OFTrue;
+
+  // the Predecessor Documents Sequence
+  if (key == DCM_PredecessorDocumentsSequence) return OFTrue;
+
+  // the Observation DateTime
+  if (key == DCM_ObservationDateTime) return OFTrue;
+
+  // all attributes of the SR Document Content Module that are present
+  if (key == DCM_ValueType) return OFTrue;
+  if (key == DCM_ConceptNameCodeSequence) return OFTrue;
+  if (key == DCM_ContinuityOfContent) return OFTrue;
+  if (key == DCM_ContentTemplateSequence) return OFTrue;
+  // if (key == DCM_ObservationDateTime) return OFTrue; // see above
+  if (key == DCM_ObservationUID) return OFTrue;
+  if (key == DCM_ContentSequence) return OFTrue;
+
+  return OFFalse;
+}
+
+
+OFBool SiStructuredReportingProfile::checkRequiredAttributeList(DcmAttributeTag& tagList) const
+{
+  OFBool result =
+    containsTag(tagList, DCM_SOPClassUID) &&
+    containsTag(tagList, DCM_StudyInstanceUID) &&
+    containsTag(tagList, DCM_SeriesInstanceUID);
+
+  // The wording in DICOM part 15 seems to indicate that the following
+  // attributes must also be signed unconditionally. However, since they
+  // optional (type 1c or type 3) and thus not present in all
+  // valid SR documents, we do not treat them as attributes that cause
+  // signature validation according to this profile to fail if absent.
+  // We include them in the list of attributes that must be signed if present:
+  //
+  // - DCM_CurrentRequestedProcedureEvidenceSequence
+  // - DCM_PertinentOtherEvidenceSequence
+  // - DCM_PredecessorDocumentsSequence
+  // - DCM_ObservationDateTime
+
+  return result;
+}
+
+
+static OFBool haveVerificationSignature(DcmItem& item)
+{
+  signed long itemNo = 0;
+  DcmItem *ditem = NULL;
+  DcmItem *ditem2 = NULL;
+  OFString s;
+  while (1)
+  {
+    if (item.findAndGetSequenceItem(DCM_DigitalSignaturesSequence, ditem, itemNo).good() && ditem)
+    {
+      if (ditem->findAndGetSequenceItem(DCM_DigitalSignaturePurposeCodeSequence, ditem2).good() && ditem2)
+      {
+        if (ditem2->findAndGetOFString(DCM_CodeValue, s).good())
+        {
+          if (s == "5") return OFTrue; // we have digital signature purpose code "5", which means that a verification signature is present
+        }
+      }
+    }
+    else return OFFalse; // no (further) item found. There is no verification signature
+
+    // check next item
+    ++itemNo;
+  }
+}
+
+
+OFCondition SiStructuredReportingProfile::inspectSignatureDataset(DcmItem& item)
+{
+  DcmElement *delem;
+  OFString s;
+
+  // check if this is an SR document by looking up the most important
+  // attributes we expect in any SR document
+  if (item.findAndGetElement(DCM_ValueType, delem).good() &&
+      item.findAndGetElement(DCM_ConceptNameCodeSequence, delem).good() &&
+      item.findAndGetElement(DCM_ContentSequence, delem).good())
+  {
+    // fine, this is an SR document
+    if (item.findAndGetOFString(DCM_VerificationFlag, s).good() && (s == "VERIFIED"))
+    {
+      // check if we already have a verification signature in this dataset
+      if (! haveVerificationSignature(item))
+      {
+        DCMSIGN_WARN("SR document status is 'VERIFIED', but the verification signature is missing");
+      }
+    }
+    return EC_Normal;
+  }
+  else
+  {
+    // not an SR document
+    return SI_EC_DatasetDoesNotMatchProfile;
+  }
+}
+
+OFBool SiStructuredReportingProfile::mainDatasetRequired() const
+{
+  return OFTrue;
+}
+
+#else /* WITH_OPENSSL */
+
+int sisrpr_cc_dummy_to_keep_linker_from_moaning = 0;
+
+#endif
diff --git a/dcmsign/libsrc/sisrvpr.cc b/dcmsign/libsrc/sisrvpr.cc
new file mode 100644 (file)
index 0000000..de6b61b
--- /dev/null
@@ -0,0 +1,101 @@
+/*
+ *
+ *  Copyright (C) 2019, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmsign
+ *
+ *  Author: Marco Eichelberg
+ *
+ *  Purpose:
+ *    classes: SiStructuredReportingVerificationProfile
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#ifdef WITH_OPENSSL
+
+#include "dcmtk/dcmsign/sisrvpr.h"
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmdata/dcitem.h"
+#include "dcmtk/dcmsign/sitypes.h"
+
+OFBool SiStructuredReportingVerificationProfile::attributeRequiredIfPresent(const DcmTagKey& key) const
+{
+
+  // call base class implementation
+  if (SiStructuredReportingProfile::attributeRequiredIfPresent(key)) return OFTrue;
+
+  // check additional keys required for a verification signature
+  if (key == DCM_SOPInstanceUID) return OFTrue;
+  if (key == DCM_VerificationFlag) return OFTrue; // Type 1 in SR Document General Module
+  if (key == DCM_VerifyingObserverSequence) return OFTrue; // Type 1C, must be present if VerificationFlag == VERIFIED
+  if (key == DCM_VerificationDateTime) return OFTrue;
+
+  return OFFalse;
+}
+
+
+OFBool SiStructuredReportingVerificationProfile::checkRequiredAttributeList(DcmAttributeTag& tagList) const
+{
+  OFBool result = SiStructuredReportingProfile::checkRequiredAttributeList(tagList);
+
+  result = result &&
+    containsTag(tagList, DCM_SOPInstanceUID) &&
+    containsTag(tagList, DCM_VerificationFlag) &&
+    containsTag(tagList, DCM_VerifyingObserverSequence);
+
+  // The wording in DICOM part 15 seems to indicate that ObservationDateTime
+  // must also be signed unconditionally. However, ObservationDateTime is actually
+  // an attribute within the VerifyingObserverSequence and will thus not be listed
+  // explicitly in tagList.
+
+  return result;
+}
+
+
+OFCondition SiStructuredReportingVerificationProfile::inspectSignatureDataset(DcmItem & item)
+{
+  DcmElement *delem;
+  OFString s;
+
+  // check if this is an SR document by looking up the most important
+  // attributes we expect in any SR document
+  if (item.findAndGetElement(DCM_ValueType, delem).good() &&
+      item.findAndGetElement(DCM_ConceptNameCodeSequence, delem).good() &&
+      item.findAndGetElement(DCM_ContentSequence, delem).good())
+  {
+    // fine, this is an SR document
+    if (item.findAndGetOFString(DCM_VerificationFlag, s).bad() || (s != "VERIFIED"))
+    {
+      // SR document status is not 'VERIFIED', cannot apply SR RSA Digital Signature Profile verification signature
+      return SI_EC_DatasetDoesNotMatchProfile;
+    }
+    return EC_Normal;
+  }
+  else
+  {
+    // not an SR document
+    return SI_EC_DatasetDoesNotMatchProfile;
+  }
+}
+
+SiSignaturePurpose::E_SignaturePurposeType SiStructuredReportingVerificationProfile::getOverrideSignaturePurpose() const
+{
+  return SiSignaturePurpose::ESP_VerificationSignature;
+}
+
+#else /* WITH_OPENSSL */
+
+int sisrvpr_cc_dummy_to_keep_linker_from_moaning = 0;
+
+#endif
diff --git a/dcmsign/libsrc/sitsfs.cc b/dcmsign/libsrc/sitsfs.cc
new file mode 100644 (file)
index 0000000..049feac
--- /dev/null
@@ -0,0 +1,226 @@
+/*
+ *
+ *  Copyright (C) 2019-2020, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmsign
+ *
+ *  Author: Marco Eichelberg
+ *
+ *  Purpose:
+ *    classes: SiTimeStamp
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#ifdef WITH_OPENSSL
+
+#include "dcmtk/dcmsign/sitsfs.h"
+#include "dcmtk/dcmdata/dcerror.h"   /* for EC_IllegalCall */
+#include "dcmtk/dcmdata/dcfilefo.h"  /* for class DcmFileFormat */
+#include "dcmtk/dcmdata/dcdeftag.h"  /* for DCM_DigitalSignatureUID */
+
+BEGIN_EXTERN_C
+#include <openssl/ts.h>
+#include <openssl/bio.h>
+END_EXTERN_C
+
+
+
+SiTimeStampFS::SiTimeStampFS()
+: SiTimeStamp()
+, tsqFilename_()
+, tsrFilename_()
+, uidFilename_()
+{
+}
+
+
+SiTimeStampFS::~SiTimeStampFS()
+{
+}
+
+
+void SiTimeStampFS::setTSQFilename(const char *fname)
+{
+  if (fname)
+    tsqFilename_ = fname;
+    else tsqFilename_ = "";
+}
+
+
+void SiTimeStampFS::setTSRFilename(const char *fname)
+{
+  if (fname)
+    tsrFilename_ = fname;
+    else tsrFilename_ = "";
+}
+
+
+void SiTimeStampFS::setUIDFilename(const char *fname)
+{
+  if (fname)
+    uidFilename_ = fname;
+    else uidFilename_ = "";
+}
+
+
+OFCondition SiTimeStampFS::stamp(
+    const unsigned char *inputData,
+    unsigned long inputDataSize)
+{
+  return create_ts_query(inputData, inputDataSize);
+}
+
+
+OFCondition SiTimeStampFS::write(DcmItem& item)
+{
+
+  TS_REQ *query = getTSQ();
+  if (query == NULL)
+  {
+    DCMSIGN_ERROR("No timestamp query object available, cannot write to file.");
+    return EC_IllegalCall;
+  }
+
+  OFCondition result = EC_Normal;
+
+  // first we write the time stamp query file
+  if (tsqFilename_.length() == 0)
+  {
+    DCMSIGN_WARN("Name of timestamp query file not set, will not write file.");
+  }
+  else
+  {
+    BIO *out_bio = BIO_new_file(tsqFilename_.c_str(), "wb");
+    if (out_bio == NULL)
+    {
+      DCMSIGN_WARN("Unable to create time stamp query file '" << tsqFilename_ << "'");
+      result = SI_EC_CannotWriteTSQ;
+    }
+    else
+    {
+      if (!i2d_TS_REQ_bio(out_bio, query))
+      {
+        DCMSIGN_WARN("Writing time stamp query file '" << tsqFilename_ << "' failed");
+        result = SI_EC_CannotWriteTSQ;
+      }
+      BIO_free_all(out_bio);
+    }
+  }
+
+  if (result.bad()) return result;
+
+  // now we write the UID file
+  if (uidFilename_.length() == 0)
+  {
+    DCMSIGN_WARN("Name of UID file for time stamp query not set, will not write file.");
+  }
+  else
+  {
+    OFString uid;
+    DcmFileFormat dfile;
+    if (item.findAndGetOFString(DCM_DigitalSignatureUID, uid).good())
+    {
+      result = dfile.getDataset()->putAndInsertString(DCM_DigitalSignatureUID, uid.c_str());
+      if (result.good()) result = dfile.saveFile(uidFilename_, EXS_LittleEndianImplicit);
+    }
+    else
+    {
+      DCMSIGN_ERROR("Signature UID not found in dataset.");
+      result = EC_IllegalCall;
+    }
+  }
+
+  return result;
+}
+
+
+OFCondition SiTimeStampFS::getUIDFromFile(OFString& uid)
+{
+  if (uidFilename_.length() == 0)
+  {
+    DCMSIGN_ERROR("Cannot load UID file, filename not set");
+    return EC_IllegalCall;
+  }
+
+  DcmFileFormat dfile;
+  OFCondition result = dfile.loadFile(uidFilename_);
+  if (result.good())
+  {
+    result = dfile.getDataset()->findAndGetOFString(DCM_DigitalSignatureUID, uid);
+    if (result.bad()) DCMSIGN_ERROR("No Digital Signature UID found in  UID file '" << uidFilename_ << "'");
+  }
+  else
+  {
+    DCMSIGN_ERROR("Cannot load UID file '" << uidFilename_ << "'");
+  }
+
+  return result;
+}
+
+
+OFCondition SiTimeStampFS::load_ts_query_from_file()
+{
+  if (tsqFilename_.length() == 0)
+  {
+    DCMSIGN_ERROR("Cannot load timestamp query file, filename not set");
+    return EC_IllegalCall;
+  }
+
+  return SiTimeStamp::load_ts_query(tsqFilename_.c_str());
+}
+
+
+OFCondition SiTimeStampFS::load_ts_response_from_file()
+{
+  if (tsrFilename_.length() == 0)
+  {
+    DCMSIGN_ERROR("Cannot load timestamp response file, filename not set");
+    return EC_IllegalCall;
+  }
+
+  return SiTimeStamp::load_ts_response(tsrFilename_.c_str());
+}
+
+
+OFCondition SiTimeStampFS::check_ts_response(DcmItem& ditem)
+{
+  if (getTSQ() == NULL)
+  {
+    DCMSIGN_ERROR("Cannot check timestamp response, timestamp query not loaded");
+    return EC_IllegalCall;
+  }
+
+  if (getTSR() == NULL)
+  {
+    DCMSIGN_ERROR("Cannot check timestamp response, not loaded");
+    return EC_IllegalCall;
+  }
+
+  return  SiTimeStamp::check_ts_response(getTSQ(), getTSR(), ditem);
+
+}
+
+
+OFCondition SiTimeStampFS::write_ts_token(DcmItem& ditem)
+{
+  return SiTimeStamp::write_ts_token(getTSR(), ditem);
+}
+
+
+
+#else /* WITH_OPENSSL */
+
+int sitsfs_cc_dummy_to_keep_linker_from_moaning = 0;
+
+#endif
diff --git a/dcmsign/libsrc/sitstamp.cc b/dcmsign/libsrc/sitstamp.cc
new file mode 100644 (file)
index 0000000..ab6a524
--- /dev/null
@@ -0,0 +1,1390 @@
+/*
+ *
+ *  Copyright (C) 2019, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmsign
+ *
+ *  Author: Marco Eichelberg
+ *
+ *  Purpose:
+ *    classes: SiTimeStamp
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+
+#ifdef WITH_OPENSSL
+
+#include "dcmtk/dcmsign/sitstamp.h"
+
+#include "dcmtk/dcmdata/dcerror.h"
+#include "dcmtk/dcmdata/dcitem.h"
+#include "dcmtk/dcmdata/dcdeftag.h"
+#include "dcmtk/dcmsign/simd5.h"
+#include "dcmtk/dcmsign/siripemd.h"
+#include "dcmtk/dcmsign/sisha1.h"
+#include "dcmtk/dcmsign/sisha256.h"
+#include "dcmtk/dcmsign/sisha384.h"
+#include "dcmtk/dcmsign/sisha512.h"
+#include "dcmtk/dcmsign/sicert.h"
+#include "dcmtk/dcmsign/sicertvf.h"
+#include "dcmtk/dcmsign/dcsignat.h"
+#include "dcmtk/ofstd/ofdatime.h"
+
+BEGIN_EXTERN_C
+#include <openssl/ts.h>
+#include <openssl/err.h>
+#include <openssl/rand.h>
+#include <openssl/bn.h>
+#include <openssl/x509.h>
+END_EXTERN_C
+
+#if OPENSSL_VERSION_NUMBER < 0x10100000L || defined(LIBRESSL_VERSION_NUMBER)
+#define X509_get0_notBefore(x) X509_get_notBefore(x)
+#define X509_get0_notAfter(x) X509_get_notAfter(x)
+#define TS_STATUS_INFO_get0_status(x) (x)->status
+#define TS_STATUS_INFO_get0_text(x) (x)->text
+#define TS_STATUS_INFO_get0_failure_info(x) (x)->failure_info
+#define TS_VERIFY_CTS_set_certs(x,y) ((x)->certs = (y))
+#define TS_VERIFY_CTX_set_data(x,y) ((x)->data = (y))
+#define TS_VERIFY_CTX_set_flags(x,y) ((x)->flags = (y))
+#define TS_VERIFY_CTX_set_store(x,y) ((x)->store = (y))
+#define ASN1_STRING_get0_data(x) ASN1_STRING_data((asn1_string_st*)x)
+#endif
+
+/// maximum length of the integer nonce, in bytes
+#define NONCE_LENGTH 8
+
+/// simple RAII container class for a raw buffer
+class RAIIBuffer
+{
+public:
+  /** constructor, allocates buffer
+   *  @param len buffer size, must be > 0
+   */
+  RAIIBuffer(size_t len)
+  : buf_(new unsigned char[len])
+  , len_(len)
+  {
+  }
+
+  /// destructor
+  virtual ~RAIIBuffer()
+  {
+    delete[] buf_;
+  }
+
+  /// buffer
+  unsigned char *buf_;
+
+  /// buffer size
+  size_t len_;
+};
+
+
+SiTimeStamp::SiTimeStamp()
+: tsq_policy_()
+, tsq_mac_(EMT_SHA256)
+, tsq_use_nonce_(OFTrue)
+, tsq_certificate_requested_(OFTrue)
+, tsq_(NULL)
+, tsr_(NULL)
+, ts_(NULL)
+, tsinfo_(NULL)
+, errorCode_(0)
+, errorString_("")
+{
+}
+
+
+SiTimeStamp::~SiTimeStamp()
+{
+  TS_REQ_free(tsq_);
+  TS_RESP_free(tsr_);
+  PKCS7_free(ts_);
+  TS_TST_INFO_free(tsinfo_);
+}
+
+void SiTimeStamp::setPolicyOID(const char *oid)
+{
+  if (oid) tsq_policy_ = oid; else tsq_policy_ = "";
+}
+
+
+void SiTimeStamp::setNonce(OFBool nonce)
+{
+  tsq_use_nonce_ = nonce;
+}
+
+
+void SiTimeStamp::setCertificateRequested(OFBool creq)
+{
+  tsq_certificate_requested_ = creq;
+}
+
+void SiTimeStamp::setMAC(E_MACType mac)
+{
+  tsq_mac_ = mac;
+}
+
+
+OFCondition SiTimeStamp::create_ts_query(
+    const unsigned char *inputData,
+    unsigned long inputDataSize)
+{
+
+  // validate input parameters
+  if (inputData == NULL || inputDataSize == 0) return EC_IllegalCall;
+
+  // delete a previous time stamp query, if present
+  if (tsq_)
+  {
+    TS_REQ_free(tsq_);
+    tsq_ = NULL;
+  }
+
+  // create message digest object
+  SiMAC *mac = NULL;  // dcmsign MAC object
+  const EVP_MD *evpmd = NULL; // OpenSSL MAC object
+  switch (tsq_mac_)
+  {
+    case EMT_SHA1:
+      mac = new SiSHA1();
+      evpmd = EVP_sha1();
+      break;
+    case EMT_RIPEMD160:
+      mac = new SiRIPEMD160();
+      evpmd = EVP_ripemd160();
+      break;
+    case EMT_MD5:
+      mac = new SiMD5();
+      evpmd = EVP_md5();
+      break;
+    case EMT_SHA256:
+      mac = new SiSHA256();
+      evpmd = EVP_sha256();
+      break;
+    case EMT_SHA384:
+      mac = new SiSHA384();
+      evpmd = EVP_sha384();
+      break;
+    case EMT_SHA512:
+      mac = new SiSHA512();
+      evpmd = EVP_sha512();
+      break;
+    default:
+      DCMSIGN_WARN("Unsupported MAC algorithm for timestamp selected.");
+      return SI_EC_UnsupportedMAC;
+      break;
+  }
+  if (mac == NULL || evpmd == NULL) return EC_MemoryExhausted;
+
+  // compute message digest
+  OFCondition result = EC_Normal;
+  RAIIBuffer md(mac->getSize());
+  result = mac->initialize();
+  if (result.good()) result = mac->digest(inputData, inputDataSize);
+  if (result.good()) result = mac->finalize(md.buf_);
+
+  // delete message digest object
+  delete mac;
+
+  if (result.good())
+  {
+    // create time stamp request, algorithm and message imprint objects
+    tsq_ = TS_REQ_new();
+    X509_ALGOR *algo = X509_ALGOR_new();
+    TS_MSG_IMPRINT *msg_imprint = TS_MSG_IMPRINT_new();
+    if (tsq_ && algo && msg_imprint)
+    {
+      // set time stamp query version (always 1)
+      if (!TS_REQ_set_version(tsq_, 1)) result = SI_EC_OpenSSLFailure;
+
+      // set message digest type
+      if (result.good())
+      {
+        if (NULL == (algo->algorithm = OBJ_nid2obj(EVP_MD_type(evpmd)))) result = SI_EC_OpenSSLFailure;
+      }
+
+      // create parameter object
+      if (result.good())
+      {
+        if (NULL == (algo->parameter = ASN1_TYPE_new())) result = EC_MemoryExhausted;
+      }
+
+      // copy algorithm object into message imprint
+      if (result.good())
+      {
+        algo->parameter->type = V_ASN1_NULL;
+        if (!TS_MSG_IMPRINT_set_algo(msg_imprint, algo)) result = SI_EC_OpenSSLFailure;
+      }
+
+      // copy message digest into message imprint
+      if (result.good())
+      {
+        if (!TS_MSG_IMPRINT_set_msg(msg_imprint, md.buf_, OFstatic_cast(int, md.len_))) result = SI_EC_OpenSSLFailure;
+      }
+
+      // copy message imprint into time stamp query
+      if (result.good())
+      {
+        if (!TS_REQ_set_msg_imprint(tsq_, msg_imprint)) result = SI_EC_OpenSSLFailure;
+      }
+
+      // set certificate requested flag
+      if (result.good())
+      {
+        if (!TS_REQ_set_cert_req(tsq_, (tsq_certificate_requested_ ? 1: 0))) result = SI_EC_OpenSSLFailure;
+      }
+    }
+    else result = EC_MemoryExhausted;
+
+    // delete algorithm object
+    X509_ALGOR_free(algo);
+
+    // delete message imprint object
+    TS_MSG_IMPRINT_free(msg_imprint);
+
+    // now we check the optional components of a time stamp query
+
+    // policy OID
+    if (result.good() && (tsq_policy_.length() > 0))
+    {
+      ASN1_OBJECT *policy_obj = OBJ_txt2obj(tsq_policy_.c_str(), 0);
+      if (policy_obj)
+      {
+        // copy policy object into time stamp query
+        if (!TS_REQ_set_policy_id(tsq_, policy_obj)) result = SI_EC_OpenSSLFailure;
+
+        // delete policy object
+        ASN1_OBJECT_free(policy_obj);
+      }
+      else
+      {
+        DCMSIGN_WARN("Cannot convert " << tsq_policy_ << " to OID.");
+        result = SI_EC_InvalidOID;
+      }
+    }
+
+    // nonce (pseudo-random integer used as protection against replay attacks)
+    if (result.good() && tsq_use_nonce_)
+    {
+      // create buffer for random data
+      unsigned char nonce_buf[NONCE_LENGTH];
+
+      // fill buffer with random data
+      if (RAND_bytes(nonce_buf, NONCE_LENGTH) <= 0) result = SI_EC_OpenSSLFailure;
+
+      if (result.good())
+      {
+        // create nonce object
+        ASN1_INTEGER *nonce_asn1 = ASN1_INTEGER_new();
+
+        if (nonce_asn1)
+        {
+          // free memory buffer of nonce_asn1 (we will create a new one)
+          OPENSSL_free(nonce_asn1->data);
+
+          // Find the first non-zero byte in the buffer
+          int i = 0;
+          for (i = 0; i < NONCE_LENGTH && !nonce_buf[i]; ++i)
+            continue;
+
+          // create a new memory buffer for nonce_asn1
+          nonce_asn1->length = NONCE_LENGTH - i;
+          nonce_asn1->data = OFreinterpret_cast(unsigned char *, OPENSSL_malloc(nonce_asn1->length + 1));
+          if (NULL != nonce_asn1->data)
+          {
+              // copy random data into nonce. The first byte is guaranteed to be nonzero,
+              // which is necessary because otherwise the field might violate DER encoding.
+              memcpy(nonce_asn1->data, nonce_buf + i, nonce_asn1->length);
+          }
+          else result = EC_MemoryExhausted;
+
+          if (result.good())
+          {
+            // copy policy object into time stamp query
+            if (!TS_REQ_set_nonce(tsq_, nonce_asn1)) result = SI_EC_OpenSSLFailure;
+          }
+
+          // delete nonce object
+          ASN1_INTEGER_free(nonce_asn1);
+        }
+        else result = EC_MemoryExhausted;
+      }
+    }
+  }
+
+  return result;
+}
+
+///helper structure for status bit arrays.
+struct StatusMap
+{
+  int bit;
+  const char *text;
+};
+
+/** status flags for timestamp resonse failures
+ *  Source: OpenSSL, ts_rsp_print.c
+ */
+static StatusMap failure_map[] =
+{
+  {TS_INFO_BAD_ALG,
+   "unrecognized or unsupported algorithm identifier"},
+  {TS_INFO_BAD_REQUEST,
+   "transaction not permitted or supported"},
+  {TS_INFO_BAD_DATA_FORMAT,
+   "the data submitted has the wrong format"},
+  {TS_INFO_TIME_NOT_AVAILABLE,
+   "the TSA's time source is not available"},
+  {TS_INFO_UNACCEPTED_POLICY,
+   "the requested TSA policy is not supported by the TSA"},
+  {TS_INFO_UNACCEPTED_EXTENSION,
+   "the requested extension is not supported by the TSA"},
+  {TS_INFO_ADD_INFO_NOT_AVAILABLE,
+   "the additional information requested could not be understood "
+   "or is not available"},
+  {TS_INFO_SYSTEM_FAILURE,
+   "the request cannot be handled due to system failure"},
+  {-1, NULL}
+};
+
+OFCondition SiTimeStamp::check_ts_response(
+    TS_REQ *tsq,
+    TS_RESP *tsr,
+    DcmItem& ditem)
+{
+  if (tsr == NULL) return EC_IllegalCall;
+
+  // retrieve status structure from timestamp response.
+  // This function does not create a copy that we need to release later.
+  TS_STATUS_INFO *status = TS_RESP_get_status_info(tsr);
+  if (status == NULL)
+  {
+    DCMSIGN_ERROR("unable to access status structure of timestamp response message");
+    return SI_EC_InvalidTSR;
+  }
+
+  // evaluate status structure from timestamp response
+  OFCondition result = EC_Normal;
+  long status_value = ASN1_INTEGER_get(TS_STATUS_INFO_get0_status(status));
+
+  if (status_value != 0) // status 0 means "granted", i.e. success
+  {
+     if (status_value == 1) DCMSIGN_WARN("timestamp response status: granted with modifications");
+     else
+     {
+       result = SI_EC_InvalidTSR;
+       switch (status_value)
+       {
+         case 2:
+           DCMSIGN_ERROR("timestamp response status: rejected");
+           break;
+         case 3:
+           DCMSIGN_ERROR("timestamp response status: waiting");
+           break;
+         case 4:
+           DCMSIGN_ERROR("timestamp response status: revocation warning");
+           break;
+         case 5:
+           DCMSIGN_ERROR("timestamp response status: revoked");
+           break;
+         default:
+           DCMSIGN_ERROR("timestamp response status: unknown error code " << status_value);
+           break;
+       }
+     }
+
+     // if we have additional status text (optional), let's print it to the logger
+     const unsigned char *c = NULL;
+     for (int i = 0; i < sk_ASN1_UTF8STRING_num(TS_STATUS_INFO_get0_text(status)); ++i)
+     {
+       c = ASN1_STRING_get0_data(sk_ASN1_UTF8STRING_value(TS_STATUS_INFO_get0_text(status), i));
+       if (c) DCMSIGN_WARN("timestamp response status text: " << c);
+     }
+
+     // if we have additional failure info flags (optional), let's print them to the logger
+     if (TS_STATUS_INFO_get0_failure_info(status) != NULL)
+     {
+      const StatusMap *fmap = failure_map;
+      for (; fmap->bit >= 0; ++fmap)
+      {
+        if (ASN1_BIT_STRING_get_bit(TS_STATUS_INFO_get0_failure_info(status), fmap->bit))
+        {
+          DCMSIGN_WARN("timestamp response status text: " << fmap->text);
+        }
+      }
+    }
+  }
+
+  TS_TST_INFO *ts_info = NULL;
+
+  // access TSTInfo structure (i.e. the content of the signed timestamp)
+  if (result.good())
+  {
+    ts_info = TS_RESP_get_tst_info(tsr);
+    if (ts_info == NULL)
+    {
+      DCMSIGN_ERROR("timestamp response does not contain TSTInfo structure");
+      result = SI_EC_InvalidTSR;
+    }
+  }
+
+  // check version number of timestamp response
+  if (result.good())
+  {
+    if (TS_TST_INFO_get_version(ts_info) != 1)
+    {
+      DCMSIGN_ERROR("unsupported timestamp response version number " << TS_TST_INFO_get_version(ts_info));
+      result =  SI_EC_InvalidTSR;
+    }
+  }
+
+  // access TSR message imprint (MAC algorithm and hash)
+  TS_MSG_IMPRINT *ts_info_imprint = NULL;
+  if (result.good())
+  {
+    ts_info_imprint = TS_TST_INFO_get_msg_imprint(ts_info);
+    if (ts_info_imprint == NULL)
+    {
+      DCMSIGN_ERROR("timestamp response validation failed: message imprint missing in timestamp response");
+      result = SI_EC_InvalidTSR;
+    }
+  }
+
+  // access TSR MAC algorithm OID
+  X509_ALGOR *ts_info_algo = NULL;
+  if (result.good())
+  {
+    ts_info_algo = TS_MSG_IMPRINT_get_algo(ts_info_imprint);
+    if (ts_info_algo == NULL)
+    {
+      DCMSIGN_ERROR("timestamp response validation failed: message digest algorithm missing in timestamp response");
+      result = SI_EC_InvalidTSR;
+    }
+  }
+
+  // bail out if the timestamp response had an error status
+  if (result.bad()) return result;
+
+  // check if the timestamp response matches the timestamp query
+  if (tsq == NULL)
+  {
+    DCMSIGN_WARN("timestamp query not available, will not check consistency with timestamp response");
+  }
+  else
+  {
+    // at this point, tsq and ts_info are guaranteed to be valid pointers.
+
+    // access message imprints (MAC algorithm and hash)
+    TS_MSG_IMPRINT *tsq_imprint = TS_REQ_get_msg_imprint(tsq);
+    if (tsq_imprint)
+    {
+      // compare message imprints
+      X509_ALGOR *tsq_algo = TS_MSG_IMPRINT_get_algo(tsq_imprint);
+      if (tsq_algo == NULL)
+      {
+        DCMSIGN_ERROR("timestamp response validation failed: message digest algorithm missing in timestamp query");
+        result = SI_EC_InvalidTSR;
+      }
+      else
+      {
+        if (OBJ_cmp(tsq_algo->algorithm, ts_info_algo->algorithm))
+        {
+          DCMSIGN_ERROR("timestamp response validation failed: message digest algorithms are different in timestamp query and response");
+          result = SI_EC_InvalidTSR;
+        }
+        else
+        {
+          unsigned int tsq_len = ASN1_STRING_length(TS_MSG_IMPRINT_get_msg(tsq_imprint));
+          unsigned int ts_info_len = ASN1_STRING_length(TS_MSG_IMPRINT_get_msg(ts_info_imprint));
+          if (tsq_len != ts_info_len)
+          {
+            DCMSIGN_ERROR("timestamp response validation failed: message digest lengths are different in timestamp query and response");
+            result = SI_EC_InvalidTSR;
+          }
+          else
+          {
+            if (memcmp(ASN1_STRING_get0_data(TS_MSG_IMPRINT_get_msg(tsq_imprint)),
+                ASN1_STRING_get0_data(TS_MSG_IMPRINT_get_msg(ts_info_imprint)), tsq_len) != 0)
+            {
+              DCMSIGN_ERROR("timestamp response validation failed: message digests do not match in timestamp query and response");
+              result = SI_EC_InvalidTSR;
+            }
+          }
+        }
+      }
+    }
+    else
+    {
+      DCMSIGN_ERROR("timestamp response validation failed: message imprint missing in timestamp query");
+      result = SI_EC_InvalidTSR;
+    }
+    if (result.bad()) return result;
+
+    // check nonces for consistency
+    const ASN1_INTEGER *tsq_nonce = TS_REQ_get_nonce(tsq);
+    if (tsq_nonce) // the timestamp query may or may not contain a nonce
+    {
+       // query contains a nonce, therefore, the response MUST also contain a nonce
+       // with the same value
+      const ASN1_INTEGER *ts_info_nonce = TS_TST_INFO_get_nonce(ts_info);
+      if (ts_info_nonce == NULL)
+      {
+        DCMSIGN_ERROR("timestamp response validation failed: nonce is missing in timestamp response");
+        result = SI_EC_InvalidTSR;
+      }
+      else
+      {
+        // compare nonces
+        if (ASN1_INTEGER_cmp(tsq_nonce, ts_info_nonce) != 0)
+        {
+          DCMSIGN_ERROR("timestamp response validation failed: nonces are not equal in timestamp query and response");
+          result = SI_EC_InvalidTSR;
+        }
+      }
+    }
+    if (result.bad()) return result;
+
+    // check policy OIDs for consistency
+    ASN1_OBJECT *tsq_policy = TS_REQ_get_policy_id(tsq);
+    if (tsq_policy) // the timestamp query may or may not contain a policy OID
+    {
+      const ASN1_OBJECT *ts_info_policy = TS_TST_INFO_get_policy_id(ts_info);
+      if (ts_info_policy == NULL)
+      {
+        DCMSIGN_ERROR("timestamp response validation failed: policy OID is missing in timestamp response");
+        result = SI_EC_InvalidTSR;
+      }
+      else
+      {
+        // compare policy OIDs
+        if (OBJ_cmp(tsq_policy, ts_info_policy) != 0)
+        {
+          DCMSIGN_ERROR("timestamp response validation failed: policy OIDs are not equal in timestamp query and response");
+          result = SI_EC_InvalidTSR;
+        }
+      }
+    }
+    if (result.bad()) return result;
+  }
+
+  // the timestamp response looks OK and is consistent with the timestamp query;
+  // now let's check consistency with the DICOM signature.
+
+  // get the signature from the DICOM dataset
+  const Uint8 *signature = NULL;
+  unsigned long sigLength = 0;
+  result = ditem.findAndGetUint8Array(DCM_Signature, signature, &sigLength);
+  if (result.bad() || sigLength < 4 || (signature == NULL))
+  {
+    DCMSIGN_ERROR("timestamp response validation failed: signature in DICOM dataset not found or invalid");
+    result = SI_EC_InvalidTSR;
+  }
+
+  // determine type of signature
+  E_KeyType signatureType = EKT_none;
+  if (result.good())
+  {
+    SiCertificate cert;
+    result = cert.read(ditem);
+    if (result.good()) signatureType = cert.getKeyType();
+    else
+    {
+      DCMSIGN_ERROR("timestamp response validation failed: certificate in DICOM dataset not found or invalid");
+      result = SI_EC_InvalidTSR;
+    }
+  }
+
+  // if the signature type is DSA or ECDSA, we need to account for a possible pad byte
+  if (result.good())
+  {
+    if (signatureType == EKT_DSA || signatureType == EKT_EC)
+    {
+      DcmSignature::adjustASN1SequenceLength(signature, sigLength);
+    }
+  }
+
+  // now determine the MAC algorithm we need to feed the signature to
+  SiMAC *mac = NULL;
+  if (result.good())
+  {
+#if OPENSSL_VERSION_NUMBER < 0x10100000L
+    ASN1_OBJECT *mac_oid = NULL;
+    void *ppval = NULL;
+#else
+    const ASN1_OBJECT *mac_oid = NULL;
+    const void *ppval = NULL;
+#endif
+    int pptype = 0;
+    X509_ALGOR_get0(&mac_oid, &pptype, &ppval, ts_info_algo);
+    if (mac_oid == NULL)
+    {
+      DCMSIGN_ERROR("timestamp response validation failed: cannot determine MAC algorithm in timestamp response");
+      result = SI_EC_InvalidTSR;
+    }
+    else
+    {
+      int mac_nid = OBJ_obj2nid(mac_oid);
+      const char *mac_name = OBJ_nid2ln(mac_nid);
+      switch (mac_nid)
+      {
+        case NID_sha1:
+          mac = new SiSHA1();
+          break;
+        case NID_ripemd160:
+          mac = new SiRIPEMD160();
+          break;
+        case NID_md5:
+          mac = new SiMD5();
+          break;
+        case NID_sha256:
+          mac = new SiSHA256();
+          break;
+        case NID_sha384:
+          mac = new SiSHA384();
+          break;
+        case NID_sha512:
+          mac = new SiSHA512();
+          break;
+        default:
+          DCMSIGN_ERROR("timestamp response validation failed: unsupported MAC algorithm " << ( mac_name ? mac_name : "(unknown)") << " in timestamp response");
+          result = SI_EC_InvalidTSR;
+          break;
+      }
+    }
+  }
+
+  // check that the lenghts of both MACs are really the same
+  if (result.good())
+  {
+    // mac is now guaranteed to point to a valid SiMAC object
+    unsigned int ts_info_len = ASN1_STRING_length(TS_MSG_IMPRINT_get_msg(ts_info_imprint));
+    if (mac->getSize() != ts_info_len)
+    {
+      DCMSIGN_ERROR("timestamp response validation failed: message digest length does not match in DICOM dataset and timestamp response");
+      result = SI_EC_InvalidTSR;
+    }
+  }
+
+  // compute MAC of digital signature and compare with the MAC in the TSR
+  if (result.good())
+  {
+    RAIIBuffer md(mac->getSize());
+    result = mac->initialize();
+    if (result.good()) result = mac->digest(signature, sigLength);
+    if (result.good()) result = mac->finalize(md.buf_);
+    if (memcmp(md.buf_, ASN1_STRING_get0_data(TS_MSG_IMPRINT_get_msg(ts_info_imprint)), mac->getSize()) != 0)
+    {
+      DCMSIGN_ERROR("timestamp response validation failed: message digests do not match in DICOM dataset and timestamp response");
+      result = SI_EC_InvalidTSR;
+    }
+  }
+
+  // delete message digest object
+  delete mac;
+
+  // Done. If we have found not problem at this point, the TSR is successful and matches
+  // both the TSQ (if present) and the DICOM dataset.
+  return result;
+}
+
+
+OFCondition SiTimeStamp::load_ts_query(const char *fname)
+{
+  if (fname == NULL) return EC_InvalidFilename;
+  TS_REQ_free(tsq_);
+  tsq_ = NULL;
+
+  OFCondition result = EC_Normal;
+  BIO *in_bio = BIO_new_file(fname, "rb");
+  if ((in_bio == NULL) || (NULL == (tsq_ = d2i_TS_REQ_bio(in_bio, NULL))))
+  {
+    DCMSIGN_ERROR("Unable to load timestamp query file '" << fname << "'");
+    result = SI_EC_CannotRead;
+  }
+  BIO_free_all(in_bio);
+  return result;
+}
+
+
+OFCondition SiTimeStamp::load_ts_response(const char *fname)
+{
+  if (fname == NULL) return EC_InvalidFilename;
+  TS_RESP_free(tsr_);
+  tsr_ = NULL;
+
+  OFCondition result = EC_Normal;
+  BIO *in_bio = BIO_new_file(fname, "rb");
+  if ((in_bio == NULL) || (NULL == (tsr_ = d2i_TS_RESP_bio(in_bio, NULL))))
+  {
+    DCMSIGN_ERROR("Unable to load timestamp response file '" << fname << "'");
+    result = SI_EC_CannotRead;
+  }
+  BIO_free_all(in_bio);
+  return result;
+}
+
+
+OFCondition SiTimeStamp::write_ts_token(
+    TS_RESP *tsr,
+    DcmItem& ditem)
+{
+  if (tsr == NULL)
+  {
+    DCMSIGN_ERROR("Cannot insert timestamp response into DICOM dataset, not loaded");
+    return EC_IllegalCall;
+  }
+
+  PKCS7 *ts_token = TS_RESP_get_token(tsr);
+  if (ts_token == NULL)
+  {
+    DCMSIGN_ERROR("No timestamp token in the timestamp respone");
+    return SI_EC_InvalidTSR;
+  }
+
+  // write timestamp token to buffer
+  OFCondition result = EC_Normal;
+  unsigned char *ts_token_buf = NULL;
+  int len = i2d_PKCS7(ts_token, &ts_token_buf);
+
+  if (len < 0)
+  {
+    DCMSIGN_ERROR("Error while serializing timestamp token");
+    result = SI_EC_OpenSSLFailure;
+  }
+
+  if (result.good()) result = ditem.putAndInsertUint8Array(DCM_CertifiedTimestamp, ts_token_buf, len);
+  if (result.good()) result = ditem.putAndInsertString(DCM_CertifiedTimestampType, "CMS_TSP");
+
+  OPENSSL_free(ts_token_buf);
+  return result;
+}
+
+
+OFCondition SiTimeStamp::read(DcmItem& item)
+{
+  OFString tstype;
+  const Uint8 *tsbytes = NULL;
+  unsigned long tslen = 0;
+
+  // delete any prior timestamp ticket
+  PKCS7_free(ts_);
+  ts_ = NULL;
+  TS_TST_INFO_free(tsinfo_);
+  tsinfo_ = NULL;
+
+  // check certified timestamp type
+  OFCondition result = item.findAndGetOFString(DCM_CertifiedTimestampType, tstype);
+  if (result.good())
+  {
+     if (tstype == "CMS_TSP")
+     {
+       // access certified timestamp
+       result = item.findAndGetUint8Array(DCM_CertifiedTimestamp, tsbytes, &tslen);
+       if (result.good())
+       {
+         // adjust for a possible pad byte
+         DcmSignature::adjustASN1SequenceLength(tsbytes, tslen);
+         const unsigned char *tsbytes_temp = tsbytes;
+         ts_ = d2i_PKCS7(NULL, &tsbytes_temp, tslen);
+         if (ts_ == NULL)
+         {
+           DCMSIGN_WARN("unable to read certified timestamp in dataset");
+           result = SI_EC_InvalidTimestamp;
+         }
+         else
+         {
+           // PKCS7_to_TS_TST_INFO() is an "expensive" function that parses
+           // the content of the signed timestamp ticket. Therefore, we cache
+           // the result.
+           tsinfo_ = PKCS7_to_TS_TST_INFO(ts_);
+           if (tsinfo_ == NULL)
+           {
+             DCMSIGN_WARN("unable to read certified timestamp ticket in dataset");
+             result = SI_EC_InvalidTimestamp;
+           }
+         }
+       }
+     }
+     else
+     {
+       DCMSIGN_WARN("unknown certified timestamp type: " << tstype);
+       result = SI_EC_UnknownTimestampType;
+     }
+  }
+  return result;
+}
+
+
+OFBool SiTimeStamp::have_tsinfo() const
+{
+  return (tsinfo_ != NULL);
+}
+
+long SiTimeStamp::get_tsinfo_version() const
+{
+  if (tsinfo_)
+    return TS_TST_INFO_get_version(tsinfo_);
+    else return -1;
+}
+
+
+void SiTimeStamp::get_tsinfo_policy_oid(OFString& oid) const
+{
+#define TSINFO_BUFSIZE 200
+  oid = "";
+  if (tsinfo_)
+  {
+    char buf[TSINFO_BUFSIZE]; // The OpenSSL recommends a buffer of at least 80 characters
+    buf[0]='\0'; // zero terminate buffer
+    int len = OBJ_obj2txt(buf, TSINFO_BUFSIZE, TS_TST_INFO_get_policy_id(tsinfo_), 1);
+    if (len > TSINFO_BUFSIZE)
+    {
+       DCMSIGN_WARN("timestamp policy OID truncated, length is " << len);
+    }
+    oid = buf;
+  }
+}
+
+
+void SiTimeStamp::get_tsinfo_imprint_algorithm_name(OFString& mac) const
+{
+  mac = "";
+  if (tsinfo_)
+  {
+
+    TS_MSG_IMPRINT *ts_info_imprint = TS_TST_INFO_get_msg_imprint(tsinfo_);
+    if (ts_info_imprint == NULL)
+    {
+      DCMSIGN_WARN("timestamp imprint cannot be accessed");
+    }
+    else
+    {
+      X509_ALGOR *ts_info_algo = TS_MSG_IMPRINT_get_algo(ts_info_imprint);
+      if (ts_info_algo == NULL)
+      {
+        DCMSIGN_WARN("timestamp imprint algorithm cannot be accessed");
+      }
+      else
+      {
+        char buf[TSINFO_BUFSIZE]; // The OpenSSL recommends a buffer of at least 80 characters
+        buf[0]='\0'; // zero terminate buffer
+        int len = OBJ_obj2txt(buf, TSINFO_BUFSIZE, ts_info_algo->algorithm, 0);
+        if (len > TSINFO_BUFSIZE)
+        {
+           DCMSIGN_WARN("timestamp imprint algorithm name truncated, length is " << len);
+        }
+        mac = buf;
+      }
+    }
+  }
+}
+
+
+void SiTimeStamp::get_tsinfo_serial_number(OFString& serial) const
+{
+  serial = "";
+  if (tsinfo_)
+  {
+    const ASN1_INTEGER *asn1serial = TS_TST_INFO_get_serial(tsinfo_);
+    if (asn1serial == NULL)
+    {
+      DCMSIGN_WARN("timestamp serial number cannot be accessed");
+    }
+    else
+    {
+      BIGNUM *bnserial = ASN1_INTEGER_to_BN(asn1serial, NULL); // creates new object
+      if (bnserial == NULL)
+      {
+        DCMSIGN_WARN("timestamp serial number cannot be converted to BIGNUM");
+      }
+      else
+      {
+        BIO *bio = BIO_new(BIO_s_mem());
+        if (bio)
+        {
+          char *bufptr = NULL;
+          BN_print(bio, bnserial);
+          BIO_write(bio,"\0",1); // add terminating zero
+          BIO_get_mem_data(bio, (char *)(&bufptr));
+          if (bufptr)
+          {
+            serial = "0x";
+            serial += bufptr;
+          }
+          BIO_free(bio);
+        }
+        else
+        {
+          DCMSIGN_WARN("timestamp serial number cannot be printed");
+        }
+        BN_free(bnserial);
+      }
+    }
+  }
+}
+
+
+void SiTimeStamp::get_tsinfo_nonce(OFString& nonce) const
+{
+  nonce = "";
+  if (tsinfo_)
+  {
+    const ASN1_INTEGER *asn1nonce = TS_TST_INFO_get_nonce(tsinfo_);
+    if (asn1nonce) // nonce is an optional field, may be absent
+    {
+      BIGNUM *bnnonce = ASN1_INTEGER_to_BN(asn1nonce, NULL); // creates new object
+      if (bnnonce == NULL)
+      {
+        DCMSIGN_WARN("timestamp nonce cannot be converted to BIGNUM");
+      }
+      else
+      {
+        BIO *bio = BIO_new(BIO_s_mem());
+        if (bio)
+        {
+          char *bufptr = NULL;
+          BN_print(bio, bnnonce);
+          BIO_write(bio,"\0",1); // add terminating zero
+          BIO_get_mem_data(bio, (char *)(&bufptr));
+          if (bufptr)
+          {
+            nonce = "0x";
+            nonce += bufptr;
+          }
+          BIO_free(bio);
+        }
+        else
+        {
+          DCMSIGN_WARN("timestamp nonce cannot be printed");
+        }
+        BN_free(bnnonce);
+      }
+    }
+  }
+}
+
+
+void SiTimeStamp::get_tsinfo_tsa_name(OFString& tsa) const
+{
+  tsa = "";
+  if (tsinfo_)
+  {
+    GENERAL_NAME *tsaname = TS_TST_INFO_get_tsa(tsinfo_);
+    if (tsaname) // tsa is an optional field, may be absent
+    {
+      BIO *bio = BIO_new(BIO_s_mem());
+      if (bio)
+      {
+        char *bufptr = NULL;
+        GENERAL_NAME_print(bio, tsaname);
+        BIO_write(bio,"\0",1); // add terminating zero
+        BIO_get_mem_data(bio, (char *)(&bufptr));
+        if (bufptr)
+        {
+          tsa = bufptr;
+        }
+        BIO_free(bio);
+      }
+      else
+      {
+        DCMSIGN_WARN("timestamp tsa cannot be printed");
+      }
+    }
+  }
+}
+
+
+void SiTimeStamp::get_tsinfo_accuracy(OFString& accuracy) const
+{
+  accuracy = "";
+  if (tsinfo_)
+  {
+    TS_ACCURACY *acc = TS_TST_INFO_get_accuracy(tsinfo_);
+    if (acc) // accuracy is an optional field, may be absent
+    {
+      char buf[20];
+      long sec = ASN1_INTEGER_get(TS_ACCURACY_get_seconds(acc));
+      long msec = ASN1_INTEGER_get(TS_ACCURACY_get_millis(acc));
+      long usec = ASN1_INTEGER_get(TS_ACCURACY_get_micros(acc));
+
+      if (sec >= 0)
+      {
+        OFStandard::snprintf(buf, 20, "%ld", sec);
+        accuracy = buf;
+        if (usec > 0)
+        {
+          OFStandard::snprintf(buf, 20, ".%03ld%03lds", msec, usec);
+          accuracy += buf;
+        }
+        else
+        {
+          OFStandard::snprintf(buf, 20, ".%03lds", msec);
+          accuracy += buf;
+        }
+      }
+    }
+  }
+}
+
+
+OFBool SiTimeStamp::get_tsinfo_ordering() const
+{
+  OFBool result = OFFalse; // the default
+  if (tsinfo_)
+  {
+    result = TS_TST_INFO_get_ordering(tsinfo_) ? OFTrue : OFFalse;
+  }
+  return result;
+}
+
+
+void SiTimeStamp::get_tsinfo_timestamp(OFString& ts) const
+{
+  ts = "";
+  if (tsinfo_)
+  {
+    const ASN1_GENERALIZEDTIME *gtime = TS_TST_INFO_get_time(tsinfo_);
+    if (gtime == NULL)
+    {
+      DCMSIGN_WARN("timestamp date/time cannot be accessed");
+    }
+    else
+    {
+      // ASN1_GENERALIZEDTIME is just an alias for ASN1_STRING,
+      // so we can use ASN1_STRING_get0_data() to access the raw string
+      const unsigned char *c = ASN1_STRING_get0_data(gtime);
+      if (c) ts = OFreinterpret_cast(const char *, c);
+    }
+  }
+}
+
+int SiTimeStamp::get_tsinfo_numextensions() const
+{
+  int result = 0;
+  if (tsinfo_)
+  {
+    result = TS_TST_INFO_get_ext_count(tsinfo_);
+  }
+  return result;
+}
+
+
+void SiTimeStamp::get_tsinfo_extension(OFString& ext, int idx) const
+{
+  ext = "";
+  if (tsinfo_)
+  {
+    int numextensions = TS_TST_INFO_get_ext_count(tsinfo_);
+    if (idx >= numextensions)
+    {
+      DCMSIGN_WARN("timestamp extension " << idx << " does not exist");
+    }
+    else
+    {
+      X509_EXTENSION *x509ext = TS_TST_INFO_get_ext(tsinfo_, idx);
+      if (x509ext == NULL)
+      {
+        DCMSIGN_WARN("timestamp extension " << idx << " cannot be accessed");
+      }
+      else
+      {
+        BIO *bio = BIO_new(BIO_s_mem());
+        if (bio)
+        {
+          char *bufptr = NULL;
+          X509V3_EXT_print(bio, x509ext, X509V3_EXT_PARSE_UNKNOWN, 0 /* indent */);
+          BIO_write(bio,"\0",1); // add terminating zero
+          BIO_get_mem_data(bio, (char *)(&bufptr));
+          if (bufptr)
+          {
+            ext = bufptr;
+          }
+          BIO_free(bio);
+        }
+        else
+        {
+          DCMSIGN_WARN("timestamp extension " << idx << " cannot be printed");
+        }
+      }
+    }
+  }
+}
+
+
+OFCondition SiTimeStamp::verifyTSSignature(SiCertificateVerifier& cv)
+{
+  // check if we have a timestamp object
+  if (ts_ == NULL) return EC_IllegalCall;
+
+  X509 *signerCert = NULL;
+  OFCondition result = EC_Normal;
+  OFString aString;
+  errorCode_ = 0;
+
+  // unfortunately, TS_RESP_verify_signature() only returns the certificate of the timestamp signer
+  // if the signature verification succeeds. If verification fails, e.g. because the timestamp
+  // certificate has expired, we have no way of accessing it
+  if (! TS_RESP_verify_signature(ts_, cv.getUntrustedCerts(), cv.getTrustedCertStore(), &signerCert))
+  {
+    result = SI_EC_TimestampSignatureVerificationFailed;
+    errorCode_ = ERR_get_error();
+  }
+
+  if (result.good() && signerCert)
+  {
+    // compare timestamp against validity period of the TSA certificate
+    // The timestamp should have been created while the certificate is valid.
+    const ASN1_TIME *notBefore = X509_get0_notBefore(signerCert);
+    const ASN1_TIME *notAfter = X509_get0_notAfter(signerCert);
+    const ASN1_GENERALIZEDTIME *gtime = TS_TST_INFO_get_time(tsinfo_);
+
+    OFDateTime dt_notBefore;
+    OFDateTime dt_notAfter;
+    OFDateTime dt_gtime;
+
+    if ((notBefore == NULL)||(notAfter == NULL)||(gtime == NULL)||
+      SiCertificate::convertASN1Time(notBefore, dt_notBefore).bad() ||
+      SiCertificate::convertASN1Time(notAfter, dt_notAfter).bad() ||
+      SiCertificate::convertGeneralizedTime(gtime, dt_gtime).bad())
+    {
+      errorCode_ = -1;
+      errorString_ = "comparison of timestamp date/time with TSA certificate notBefore/notAfter attribute failed, value possibly malformed.";
+      DCMSIGN_ERROR(errorString_);
+      result = SI_EC_TimestampSignatureVerificationFailed;
+    }
+    else
+    {
+      if (dt_gtime < dt_notBefore)
+      {
+        errorCode_ = -1;
+        errorString_ = "timestamp created before start of TSA certificate validity.";
+        DCMSIGN_ERROR(errorString_);
+        result = SI_EC_TimestampSignatureVerificationFailed;
+      }
+      else if (dt_gtime > dt_notAfter)
+      {
+        errorCode_ = -1;
+        errorString_ = "timestamp created after expiry of TSA certificate.";
+        DCMSIGN_ERROR(errorString_);
+        result = SI_EC_TimestampSignatureVerificationFailed;
+      }
+    }
+  }
+
+  // wrap certificate into a SiCertificate instance that will also free
+  // the memory when it goes out of scope.
+  // SiCertificate gracefully handles the case where signerCert is NULL.
+  SiCertificate cert(signerCert);
+
+  if (signerCert && dcmsignLogger.isEnabledFor(OFLogger::INFO_LOG_LEVEL))
+  {
+    DCMSIGN_INFO("  Timestamp signature certificate: ");
+    if ((signerCert == NULL)||(cert.getKeyType()==EKT_none))
+      DCMSIGN_INFO("      none");
+    else
+    {
+      DCMSIGN_INFO("      X.509v" << cert.getX509Version());
+      cert.getCertSubjectName(aString);
+      DCMSIGN_INFO("      Subject                 : " << aString);
+      cert.getCertIssuerName(aString);
+      DCMSIGN_INFO("      Issued by               : " << aString);
+      DCMSIGN_INFO("      Serial no.              : " << cert.getCertSerialNo());
+      cert.getCertValidityNotBefore(aString);
+      DCMSIGN_INFO("      Validity                : not before " << aString);
+      cert.getCertValidityNotAfter(aString);
+      DCMSIGN_INFO("      Validity                : not after " << aString);
+      const char *ecname = NULL;
+      switch (cert.getKeyType())
+      {
+        case EKT_RSA:
+          DCMSIGN_INFO("      Public key              : RSA, " << cert.getCertKeyBits() << " bits");
+          break;
+        case EKT_DSA:
+          DCMSIGN_INFO("      Public key              : DSA, " << cert.getCertKeyBits() << " bits");
+          break;
+        case EKT_EC:
+          ecname = cert.getCertCurveName();
+          if (ecname)
+          {
+            DCMSIGN_INFO("      Public key              : EC, curve " << ecname << ", " << cert.getCertKeyBits() << " bits");
+          }
+          else
+          {
+            DCMSIGN_INFO("      Public key              : EC, " << cert.getCertKeyBits() << " bits");
+          }
+          break;
+        case EKT_DH:
+          DCMSIGN_INFO("      Public key              : DH, " << cert.getCertKeyBits() << " bits");
+          break;
+        default:
+        case EKT_none: // should never happen
+          DCMSIGN_INFO("      Public key              : unknown type");
+          break;
+      }
+    }
+  }
+  return result;
+}
+
+
+OFCondition SiTimeStamp::verifyTSToken(
+    SiCertificateVerifier& cv,
+    DcmItem& ditem,
+    SiCertificate& cert)
+{
+  // check if we have a timestamp object
+  if (ts_ == NULL) return EC_IllegalCall;
+
+  OFCondition result = EC_Normal;
+  errorCode_ = 0;
+
+  // determine type of signature
+  E_KeyType signatureType = cert.getKeyType();
+
+  // create timestamp verification context
+  TS_VERIFY_CTX *ctx = TS_VERIFY_CTX_new();
+
+  if (ctx)
+  {
+    // these are the checks we want to perform
+    TS_VERIFY_CTX_set_flags(ctx, TS_VFY_VERSION | TS_VFY_SIGNER | TS_VFY_DATA | TS_VFY_SIGNATURE);
+
+    // get the signature from the DICOM dataset
+    const Uint8 *signature = NULL;
+    unsigned long sigLength = 0;
+    result = ditem.findAndGetUint8Array(DCM_Signature, signature, &sigLength);
+    if (result.bad() || sigLength < 4 || (signature == NULL))
+    {
+      DCMSIGN_ERROR("timestamp verification failed: signature in DICOM dataset not found or invalid");
+      result = SI_EC_TimestampSignatureVerificationFailed;
+    }
+
+    // if the signature type is DSA or ECDSA, we need to account for a possible pad byte
+    if (result.good())
+    {
+      if (signatureType == EKT_DSA || signatureType == EKT_EC)
+      {
+        DcmSignature::adjustASN1SequenceLength(signature, sigLength);
+      }
+    }
+
+    if (result.good())
+    {
+
+#if OPENSSL_VERSION_NUMBER < 0x10002000L || defined(LIBRESSL_VERSION_NUMBER)
+      BIO *bio = BIO_new_mem_buf(OFconst_cast(Uint8 *, signature), sigLength);
+#else
+      BIO *bio = BIO_new_mem_buf(signature, sigLength);
+#endif
+      if (bio)
+      {
+        // set the digital signature as the raw data against which
+        // the imprint in the timestamp ticket should be checked
+        TS_VERIFY_CTX_set_data(ctx, bio);
+
+        // set certificate store and stack. Needed to verify that
+        // the TSA field in the timestamp ticket matches the signer certificate
+        TS_VERIFY_CTX_set_store(ctx, cv.getTrustedCertStore());
+        TS_VERIFY_CTS_set_certs(ctx, cv.getUntrustedCerts());
+
+        // run the verification function
+        if (! TS_RESP_verify_token(ctx, ts_))
+        {
+          result = SI_EC_TimestampSignatureVerificationFailed;
+          errorCode_ = ERR_get_error();
+        }
+
+        BIO_free(bio);
+      }
+      else
+      {
+        errorCode_ = -1;
+        errorString_ = "timestamp verification failed: cannot create memory buffer";
+        DCMSIGN_ERROR(errorString_);
+        result = SI_EC_TimestampSignatureVerificationFailed;
+      }
+    }
+
+    // prevent TS_VERIFY_CTX_free from double-deleting our objects
+    TS_VERIFY_CTX_set_data(ctx, NULL);
+    TS_VERIFY_CTX_set_store(ctx, NULL);
+    TS_VERIFY_CTS_set_certs(ctx, NULL);
+
+    TS_VERIFY_CTX_free(ctx);
+  }
+
+  if (result.good())
+  {
+    // compare timestamp against validity period of the certificate
+    // for the DICOM signature. The timestamp should have been created while the
+    // certificate is valid.
+    X509 *rawcert = cert.getRawCertificate();
+    const ASN1_TIME *notBefore = X509_get0_notBefore(rawcert);
+    const ASN1_TIME *notAfter = X509_get0_notAfter(rawcert);
+    const ASN1_GENERALIZEDTIME *gtime = TS_TST_INFO_get_time(tsinfo_);
+
+    OFDateTime dt_notBefore;
+    OFDateTime dt_notAfter;
+    OFDateTime dt_gtime;
+
+    if ((notBefore == NULL)||(notAfter == NULL)||(gtime == NULL)||
+      SiCertificate::convertASN1Time(notBefore, dt_notBefore).bad() ||
+      SiCertificate::convertASN1Time(notAfter, dt_notAfter).bad() ||
+      SiCertificate::convertGeneralizedTime(gtime, dt_gtime).bad())
+    {
+      errorCode_ = -1;
+      errorString_ = "comparison of timestamp date/time with signer certificate notBefore/notAfter attribute failed, value possibly malformed.";
+      DCMSIGN_ERROR(errorString_);
+      result = SI_EC_TimestampSignatureVerificationFailed;
+    }
+    else
+    {
+      if (dt_gtime < dt_notBefore)
+      {
+        errorCode_ = -1;
+        errorString_ = "timestamp created before start of signer certificate validity.";
+        DCMSIGN_ERROR(errorString_);
+        result = SI_EC_TimestampSignatureVerificationFailed;
+      }
+      else if (dt_gtime > dt_notAfter)
+      {
+        errorCode_ = -1;
+        errorString_ = "timestamp created after expiry of signer certificate.";
+        DCMSIGN_ERROR(errorString_);
+        result = SI_EC_TimestampSignatureVerificationFailed;
+      }
+    }
+  }
+
+  return result;
+}
+
+
+void SiTimeStamp::lastError(OFString& err) const
+{
+  if (errorCode_ < 0) err = errorString_;
+  else
+  {
+    const char *c = ERR_reason_error_string(errorCode_);
+    if (c) err = c; else err = "";
+  }
+}
+
+
+#else /* WITH_OPENSSL */
+
+int sitstamp_cc_dummy_to_keep_linker_from_moaning = 0;
+
+#endif
index 96a89157d776b6e9ffaf1682ae86dfc8dc6d1611..774b8ec169d725ace76a8f8555975f709e5e8916 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1998-2018, OFFIS e.V.
+ *  Copyright (C) 1998-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -42,8 +42,27 @@ makeOFConditionConst(SI_EC_VerificationFailed_NoSignature,             OFM_dcmsi
 makeOFConditionConst(SI_EC_VerificationFailed_UnsupportedMACAlgorithm, OFM_dcmsign, 13, OF_error, "signature verification failed: MAC algorithm not supported");
 makeOFConditionConst(SI_EC_VerificationFailed_Corrupted,               OFM_dcmsign, 14, OF_error, "signature verification failed: signature is invalid (document corrupted)");
 makeOFConditionConst(SI_EC_VerificationFailed_NoTrust,                 OFM_dcmsign, 16, OF_error, "signature verification failed: certificate issued by unknown CA");
+makeOFConditionConst(SI_EC_DatasetDoesNotMatchProfile,                 OFM_dcmsign, 17, OF_error, "dataset not suitable for the selected security profile");
+makeOFConditionConst(SI_EC_UnsupportedMAC,                             OFM_dcmsign, 18, OF_error, "unsupported MAC algorithm selected");
+makeOFConditionConst(SI_EC_InvalidOID,                                 OFM_dcmsign, 19, OF_error, "invalid object identifier (OID) string");
+makeOFConditionConst(SI_EC_CannotWriteTSQ,                             OFM_dcmsign, 20, OF_error, "unable to write time stamp query file");
+makeOFConditionConst(SI_EC_InvalidTSR,                                 OFM_dcmsign, 21, OF_error, "verification of timestamp response message failed");
+makeOFConditionConst(SI_EC_VerificationFailed_NoDataElementsSigned,    OFM_dcmsign, 22, OF_error, "signature verification failed: DataElementsSigned missing or incorrect");
+makeOFConditionConst(SI_EC_DataElementsSignedDoesNotMatchProfile,      OFM_dcmsign, 23, OF_error, "list of data elements signed does not match profile requirements");
+makeOFConditionConst(SI_EC_ItemLocationNotFound,                       OFM_dcmsign, 24, OF_error, "desired signature location not found");
+makeOFConditionConst(SI_EC_UnknownTimestampType,                       OFM_dcmsign, 25, OF_error, "unknown certified timestamp type");
+makeOFConditionConst(SI_EC_InvalidTimestamp,                           OFM_dcmsign, 26, OF_error, "certified timestamp in dataset cannot be read");
+makeOFConditionConst(SI_EC_InvalidFiletype,                            OFM_dcmsign, 27, OF_error, "filetype is unknown (neither PEM nor DER)");
+makeOFConditionConst(SI_EC_TimestampSignatureVerificationFailed,       OFM_dcmsign, 28, OF_error, "signature verification of the certified timestamp failed");
+makeOFConditionConst(SI_EC_VerificationFailed_CertExpiredAtSignature,  OFM_dcmsign, 29, OF_error, "signature verification failed: certificate was expired at signature creation date");
+makeOFConditionConst(SI_EC_VerificationFailed_CertNotYetValidAtSig,    OFM_dcmsign, 30, OF_error, "signature verification failed: certificate was not yet valid at signature creation date");
+makeOFConditionConst(SI_EC_AttributeNotSignable,                       OFM_dcmsign, 31, OF_error, "list of attributes to be signed contains attribute that is not signable");
+makeOFConditionConst(SI_EC_VerificationFailed_AttributeNotSignable,    OFM_dcmsign, 32, OF_error, "signature verification failed: signature contains attribute that is not signable");
+makeOFConditionConst(SI_EC_DatasetEmpty,                               OFM_dcmsign, 33, OF_error, "selected dataset or item is empty, nothing to sign");
+makeOFConditionConst(SI_EC_RequiredAttributeMissing,                   OFM_dcmsign, 34, OF_error, "cannot create signature for current signature profile: required attributes missing");
+makeOFConditionConst(SI_EC_EllipticCurveNotSupported,                  OFM_dcmsign, 35, OF_error, "cannot handle ECDSA signatures because OpenSSL was compiled without elliptic curve support");
 
-OFLogger DCM_dcmsignLogger = OFLog::getLogger("dcmtk.dcmsign");
+OFLogger dcmsignLogger = OFLog::getLogger("dcmtk.dcmsign");
 
 #else /* WITH_OPENSSL */
 
index 17017b5d5a0cab8162c3449f3fa0cc7aeec45059..481ff731f0212ad80afc0c8ebed622f7a2fed5a9 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID100_QuantitativeDiagnosticImagingProcedures
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:14 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:12:49 by J. Riesmeier
  *
  */
 
@@ -28,7 +28,7 @@
 
 /** Implementation of DCMR Context Group:
  *  CID 100 - Quantitative Diagnostic Imaging Procedures.
- *  (type: extensible, version: 20190121)
+ *  (type: extensible, version: 20190817)
  */
 class DCMTK_CMR_EXPORT CID100_QuantitativeDiagnosticImagingProcedures
   : public DSRContextGroup
@@ -66,7 +66,7 @@ class DCMTK_CMR_EXPORT CID100_QuantitativeDiagnosticImagingProcedures
         PETWholeBody,
         /// (443271005,SCT,"PET/CT FDG imaging of whole body")
         PETCT_FDGImagingOfWholeBody,
-        /// (443844003,SCT,"PET/CT MET imaging of whole body")
+        /// (764704008,SCT,"PET/CT MET imaging of whole body")
         PETCT_METImagingOfWholeBody,
         /// (39142-5,LN,"CT perfusion head with contrast IV")
         CTPerfusionHeadWithContrastIV,
index b9044e1bad4f6c4e9631fc0a4ba042cce367c48f..b30ac7165abe2d72e1405cbf5957312701cab317 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID10013_CTAcquisitionType
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:39 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:16 by J. Riesmeier
  *
  */
 
index dc4b0209932072c5992d1e28b19784b333f0ea9c..0b7866ea4491bf0d88fc618a0e6cf9dc6ab846b0 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID10033_CTReconstructionAlgorithm
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:41 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:18 by J. Riesmeier
  *
  */
 
index 1a7af6e2ffb577fcf6988d8efccdb97d4afb5af5..e71165adeac1d2cb739f45e2555808693df64975 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID11_RouteOfAdministration
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:09 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:12:44 by J. Riesmeier
  *
  */
 
@@ -28,7 +28,7 @@
 
 /** Implementation of DCMR Context Group:
  *  CID 11 - Route of Administration.
- *  (type: extensible, version: 20160314)
+ *  (type: extensible, version: 20200117)
  */
 class DCMTK_CMR_EXPORT CID11_RouteOfAdministration
   : public DSRContextGroup
@@ -89,7 +89,9 @@ class DCMTK_CMR_EXPORT CID11_RouteOfAdministration
         /// (372464004,SCT,"Intradermal route")
         IntradermalRoute,
         /// (447122006,SCT,"Intratumor route")
-        IntratumorRoute
+        IntratumorRoute,
+        /// (445769006,SCT,"Intracorpus cavernosum route")
+        IntracorpusCavernosumRoute
     };
 
     /** (default) constructor
index ac89b3c25184257b919ebef2d85c5f981ad8edd8..63a057cfc888825c6dffc29e9a60de44e3d3eb79 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID244_Laterality
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:16 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:12:51 by J. Riesmeier
  *
  */
 
@@ -40,9 +40,9 @@ class DCMTK_CMR_EXPORT CID244_Laterality
      */
     enum EnumType
     {
-        /// (24028007,SCT,"Right")
+        /// (24028007,SCT,"Right"), included from CID 247
         Right,
-        /// (7771000,SCT,"Left")
+        /// (7771000,SCT,"Left"), included from CID 247
         Left,
         /// (51440002,SCT,"Bilateral")
         Bilateral,
index c4351d391087341dfabc0336ca706571da6ff891..6428318470e1b16cf37e6af16ebe99c90339c351 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID29_AcquisitionModality
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:11 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:12:45 by J. Riesmeier
  *
  */
 
@@ -28,7 +28,7 @@
 
 /** Implementation of DCMR Context Group:
  *  CID 29 - Acquisition Modality.
- *  (type: extensible, version: 20190327)
+ *  (type: extensible, version: 20201115)
  */
 class DCMTK_CMR_EXPORT CID29_AcquisitionModality
   : public DSRContextGroup
@@ -42,26 +42,34 @@ class DCMTK_CMR_EXPORT CID29_AcquisitionModality
     {
         /// (AR,DCM,"Autorefraction")
         Autorefraction,
-        /// (BDUS,DCM,"Ultrasound Bone Densitometry")
-        UltrasoundBoneDensitometry,
         /// (BI,DCM,"Biomagnetic Imaging")
         BiomagneticImaging,
         /// (BMD,DCM,"Bone Mineral Densitometry")
         BoneMineralDensitometry,
+        /// (EPS,DCM,"Cardiac Electrophysiology")
+        CardiacElectrophysiology,
         /// (CR,DCM,"Computed Radiography")
         ComputedRadiography,
         /// (CT,DCM,"Computed Tomography")
         ComputedTomography,
+        /// (DMS,DCM,"Dermoscopy")
+        Dermoscopy,
         /// (DG,DCM,"Diaphanography")
         Diaphanography,
         /// (DX,DCM,"Digital Radiography")
         DigitalRadiography,
         /// (ECG,DCM,"Electrocardiography")
         Electrocardiography,
-        /// (EPS,DCM,"Cardiac Electrophysiology")
-        CardiacElectrophysiology,
+        /// (EEG,DCM,"Electroencephalography")
+        Electroencephalography,
+        /// (EMG,DCM,"Electromyography")
+        Electromyography,
+        /// (EOG,DCM,"Electrooculography")
+        Electrooculography,
         /// (ES,DCM,"Endoscopy")
         Endoscopy,
+        /// (XC,DCM,"External-camera Photography")
+        ExternalCameraPhotography,
         /// (GM,DCM,"General Microscopy")
         GeneralMicroscopy,
         /// (HD,DCM,"Hemodynamic Waveform")
@@ -74,24 +82,22 @@ class DCMTK_CMR_EXPORT CID29_AcquisitionModality
         IntravascularUltrasound,
         /// (KER,DCM,"Keratometry")
         Keratometry,
-        /// (LEN,DCM,"Lensometry")
-        Lensometry,
         /// (LS,DCM,"Laser Scan")
         LaserScan,
-        /// (MG,DCM,"Mammography")
-        Mammography,
+        /// (LEN,DCM,"Lensometry")
+        Lensometry,
         /// (MR,DCM,"Magnetic Resonance")
         MagneticResonance,
+        /// (MG,DCM,"Mammography")
+        Mammography,
         /// (NM,DCM,"Nuclear Medicine")
         NuclearMedicine,
         /// (OAM,DCM,"Ophthalmic Axial Measurements")
         OphthalmicAxialMeasurements,
-        /// (OCT,DCM,"Optical Coherence Tomography")
-        OpticalCoherenceTomography,
-        /// (OP,DCM,"Ophthalmic Photography")
-        OphthalmicPhotography,
         /// (OPM,DCM,"Ophthalmic Mapping")
         OphthalmicMapping,
+        /// (OP,DCM,"Ophthalmic Photography")
+        OphthalmicPhotography,
         /// (OPT,DCM,"Ophthalmic Tomography")
         OphthalmicTomography,
         /// (OPTBSV,DCM,"Ophthalmic Tomography B-scan Volume Analysis")
@@ -100,18 +106,22 @@ class DCMTK_CMR_EXPORT CID29_AcquisitionModality
         OphthalmicTomographyEnFace,
         /// (OPV,DCM,"Ophthalmic Visual Field")
         OphthalmicVisualField,
+        /// (OCT,DCM,"Optical Coherence Tomography")
+        OpticalCoherenceTomography,
         /// (OSS,DCM,"Optical Surface Scanner")
         OpticalSurfaceScanner,
-        /// (PT,DCM,"Positron emission tomography")
-        PositronEmissionTomography,
         /// (PX,DCM,"Panoramic X-Ray")
         PanoramicXRay,
-        /// (RESP,DCM,"Respiratory Waveform")
-        RespiratoryWaveform,
+        /// (POS,DCM,"Position Sensor")
+        PositionSensor,
+        /// (PT,DCM,"Positron emission tomography")
+        PositronEmissionTomography,
         /// (RF,DCM,"Radiofluoroscopy")
         Radiofluoroscopy,
         /// (RG,DCM,"Radiographic imaging")
         RadiographicImaging,
+        /// (RESP,DCM,"Respiratory Waveform")
+        RespiratoryWaveform,
         /// (RTIMAGE,DCM,"RT Image")
         RTImage,
         /// (SM,DCM,"Slide Microscopy")
@@ -122,12 +132,12 @@ class DCMTK_CMR_EXPORT CID29_AcquisitionModality
         Thermography,
         /// (US,DCM,"Ultrasound")
         Ultrasound,
+        /// (BDUS,DCM,"Ultrasound Bone Densitometry")
+        UltrasoundBoneDensitometry,
         /// (VA,DCM,"Visual Acuity")
         VisualAcuity,
         /// (XA,DCM,"X-Ray Angiography")
-        XRayAngiography,
-        /// (XC,DCM,"External-camera Photography")
-        ExternalCameraPhotography
+        XRayAngiography
     };
 
     /** (default) constructor
index 8bc448dd22a2143ed2600758016f90884a0e0e7c..e9ebfb44741a09c337fda513d387c32b8060a461 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID4020_PETRadionuclide
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:18 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:12:55 by J. Riesmeier
  *
  */
 
index 3a3a968e6ebb139918ca4a12460fb66a6ab1c501..1242c5a81f32e8fc3d3481e9bd1ecd4ae881f614 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID4021_PETRadiopharmaceutical
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:20 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:12:57 by J. Riesmeier
  *
  */
 
@@ -28,7 +28,7 @@
 
 /** Implementation of DCMR Context Group:
  *  CID 4021 - PET Radiopharmaceutical.
- *  (type: extensible, version: 20190124)
+ *  (type: extensible, version: 20201116)
  */
 class DCMTK_CMR_EXPORT CID4021_PETRadiopharmaceutical
   : public DSRContextGroup
@@ -40,6 +40,8 @@ class DCMTK_CMR_EXPORT CID4021_PETRadiopharmaceutical
      */
     enum EnumType
     {
+        /// (C000591008,MSH,"^18^Fluorine flortaucipir")
+        _18_FluorineFlortaucipir,
         /// (126752,DCM,"28H1 ^89^Zr")
         _28H1_89Zr,
         /// (126713,DCM,"2FA F^18^")
@@ -112,6 +114,10 @@ class DCMTK_CMR_EXPORT CID4021_PETRadiopharmaceutical
         DfFKPEG3_89Zr,
         /// (126747,DCM,"DN30 ^89^Zr")
         DN30_89Zr,
+        /// (126765,DCM,"DPA-713 ^11^C")
+        DPA713_11C,
+        /// (126766,DCM,"DPA-714 ^18^F")
+        DPA714_18F,
         /// (126519,DCM,"E4G10 ^89^Zr")
         E4G10_89Zr,
         /// (126732,DCM,"Ecromeximab ^89^Zr")
@@ -130,7 +136,7 @@ class DCMTK_CMR_EXPORT CID4021_PETRadiopharmaceutical
         Florbetaben_F18,
         /// (456995000,SCT,"Florbetapir F^18^")
         Florbetapir_F18,
-        /// (C4547429,UMLS,"Flortaucipir F^18^")
+        /// (C000591008,MSH,"Flortaucipir F^18^")
         Flortaucipir_F18,
         /// (126503,DCM,"Flubatine F^18^")
         Flubatine_F18,
@@ -154,7 +160,7 @@ class DCMTK_CMR_EXPORT CID4021_PETRadiopharmaceutical
         FluoroestradiolFES_F18,
         /// (C1541539,UMLS,"Fluoroetanidazole F^18^")
         Fluoroetanidazole_F18,
-        /// (129500005,SCT,"Fluoro-L-dopa F^18^")
+        /// (5811000122108,SCT,"Fluoro-L-dopa F^18^")
         FluoroLDopa_F18,
         /// (422763008,SCT,"Fluoromethane F^18^")
         Fluoromethane_F18,
@@ -174,7 +180,7 @@ class DCMTK_CMR_EXPORT CID4021_PETRadiopharmaceutical
         Fresolimumab_89Zr,
         /// (126731,DCM,"GA201 ^89^Zr")
         GA201_89Zr,
-        /// (129516007,SCT,"Germanium Ge^68^")
+        /// (53315004,SCT,"Germanium Ge^68^")
         Germanium_Ge68,
         /// (126724,DCM,"Glembatumumab vedotin ^89^Zr")
         GlembatumumabVedotin_89Zr,
@@ -206,7 +212,7 @@ class DCMTK_CMR_EXPORT CID4021_PETRadiopharmaceutical
         MonoclonalAntibodymAb_64Cu,
         /// (126511,DCM,"Monoclonal Antibody (mAb) ^89^Zr")
         MonoclonalAntibodymAb_89Zr,
-        /// (424874008,SCT,"Monoclonal antibody I^124^")
+        /// (423249007,SCT,"Monoclonal antibody I^124^")
         MonoclonalAntibody_I124,
         /// (126753,DCM,"Nanocolloidal albumin ^89^Zr")
         NanocolloidalAlbumin_89Zr,
@@ -230,6 +236,8 @@ class DCMTK_CMR_EXPORT CID4021_PETRadiopharmaceutical
         PinatuzumabVedotin_89Zr,
         /// (126500,DCM,"Pittsburgh compound B C^11^")
         PittsburghCompoundB_C11,
+        /// (C1609883,UMLS,"PK11195 ^11^C")
+        PK11195_11C,
         /// (126726,DCM,"Polatuzumab vedotin ^89^Zr")
         PolatuzumabVedotin_89Zr,
         /// (126758,DCM,"PSMA-1007 F^18^")
@@ -270,7 +278,7 @@ class DCMTK_CMR_EXPORT CID4021_PETRadiopharmaceutical
         SodiumFluoride_F18,
         /// (422980002,SCT,"Sodium iodide I^124^")
         SodiumIodide_I124,
-        /// (129517003,SCT,"Sodium Na^22^")
+        /// (71633006,SCT,"Sodium Na^22^")
         Sodium_Na22,
         /// (129499001,SCT,"Spiperone F^18^")
         Spiperone_F18,
index d82bf0bac344bb06667ff50a6b1b02a243345403..28e324ef899fee2409a7b878a356c92cd4be8897 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID4031_CommonAnatomicRegions
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:22 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:12:59 by J. Riesmeier
  *
  */
 
@@ -28,7 +28,7 @@
 
 /** Implementation of DCMR Context Group:
  *  CID 4031 - Common Anatomic Regions.
- *  (type: extensible, version: 20170914)
+ *  (type: extensible, version: 20200704)
  */
 class DCMTK_CMR_EXPORT CID4031_CommonAnatomicRegions
   : public DSRContextGroup
@@ -40,9 +40,9 @@ class DCMTK_CMR_EXPORT CID4031_CommonAnatomicRegions
      */
     enum EnumType
     {
-        /// (113345001,SCT,"Abdomen")
+        /// (818981001,SCT,"Abdomen")
         Abdomen,
-        /// (416949008,SCT,"Abdomen and Pelvis")
+        /// (818982008,SCT,"Abdomen and Pelvis")
         AbdomenAndPelvis,
         /// (85856004,SCT,"Acromioclavicular joint")
         AcromioclavicularJoint,
@@ -70,7 +70,7 @@ class DCMTK_CMR_EXPORT CID4031_CommonAnatomicRegions
         CervicalSpine,
         /// (297171002,SCT,"Cervico-thoracic spine")
         CervicoThoracicSpine,
-        /// (51185008,SCT,"Chest")
+        /// (816094009,SCT,"Chest")
         Chest,
         /// (416550000,SCT,"Chest and Abdomen")
         ChestAndAbdomen,
@@ -82,6 +82,8 @@ class DCMTK_CMR_EXPORT CID4031_CommonAnatomicRegions
         Coccyx,
         /// (71854001,SCT,"Colon")
         Colon,
+        /// (79741001,SCT,"Common bile duct")
+        CommonBileDuct,
         /// (38848004,SCT,"Duodenum")
         Duodenum,
         /// (16953009,SCT,"Elbow joint")
@@ -120,7 +122,9 @@ class DCMTK_CMR_EXPORT CID4031_CommonAnatomicRegions
         HeadAndNeck,
         /// (80891009,SCT,"Heart")
         Heart,
-        /// (29836001,SCT,"Hip joint")
+        /// (29836001,SCT,"Hip")
+        Hip,
+        /// (24136001,SCT,"Hip Joint")
         HipJoint,
         /// (85050009,SCT,"Humerus")
         Humerus,
@@ -140,6 +144,8 @@ class DCMTK_CMR_EXPORT CID4031_CommonAnatomicRegions
         LargeIntestine,
         /// (4596009,SCT,"Larynx")
         Larynx,
+        /// (303270005,SCT,"Liver and biliary structure")
+        LiverAndBiliaryStructure,
         /// (30021000,SCT,"Lower leg")
         LowerLeg,
         /// (61685007,SCT,"Lower limb")
@@ -174,6 +180,10 @@ class DCMTK_CMR_EXPORT CID4031_CommonAnatomicRegions
         OpticCanal,
         /// (363654007,SCT,"Orbital structure")
         OrbitalStructure,
+        /// (15776009,SCT,"Pancreas")
+        Pancreas,
+        /// (69930009,SCT,"Pancreatic duct")
+        PancreaticDuct,
         /// (110621006,SCT,"Pancreatic duct and bile duct systems")
         PancreaticDuctAndBileDuctSystems,
         /// (2095001,SCT,"Paranasal sinus")
@@ -182,7 +192,7 @@ class DCMTK_CMR_EXPORT CID4031_CommonAnatomicRegions
         ParotidGland,
         /// (64234005,SCT,"Patella")
         Patella,
-        /// (12921003,SCT,"Pelvis")
+        /// (816092008,SCT,"Pelvis")
         Pelvis,
         /// (416631005,SCT,"Pelvis and lower extremities")
         PelvisAndLowerExtremities,
@@ -194,6 +204,8 @@ class DCMTK_CMR_EXPORT CID4031_CommonAnatomicRegions
         Rectum,
         /// (113197003,SCT,"Rib")
         Rib,
+        /// (297174005,SCT,"Sacro-coccygeal Spine")
+        SacroCoccygealSpine,
         /// (39723000,SCT,"Sacroiliac joint")
         SacroiliacJoint,
         /// (54735007,SCT,"Sacrum")
index feb3501d153837b170dac4b9575af66f8f539c06..6e2df82ed30c6e604c7f39dab1c11e0d5c2b50ae 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID42_NumericValueQualifier
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:12 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:12:47 by J. Riesmeier
  *
  */
 
index 4c51a00ff82e4e871864fea9b6396e39be1cbb0e..7fc03e4e43ed0a4e271078509be7cf50509ddf79 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID6147_ResponseCriteria
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:24 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:01 by J. Riesmeier
  *
  */
 
index 2f2e005320bbab592c776bde2606412b5b1c07aa..a99eb4bec8d2dae948fc4a36db08a5f1593109ec 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID7021_MeasurementReportDocumentTitles
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:26 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:03 by J. Riesmeier
  *
  */
 
index 4a539f58bf9fba49b6cded1d5c575845affca61e..048c916e4f7f9abc95eed2b4119ffae86d1aa498 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID7181_AbstractMultiDimensionalImageModelComponentUnits
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:28 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:05 by J. Riesmeier
  *
  */
 
index bc33721b2c4ab56b75cff2e2e7c1643d92e2eac7..2567e285a78290d86be6e8d683a270135af84810 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID7445_DeviceParticipatingRoles
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:30 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:06 by J. Riesmeier
  *
  */
 
index 846037732767ee0c0f2330dc7d514dfbd808edfb..b64e0fc25a9f40d18469363e792000ad80472f39 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID7452_OrganizationalRoles
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:32 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:08 by J. Riesmeier
  *
  */
 
index 9536a07cd96de0786cfe927fb4008b5dc7ee90de..d7160ceb0c335011d4bf955b20d53461cd4e4c67 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID7453_PerformingRoles
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:33 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:10 by J. Riesmeier
  *
  */
 
index 4edd30a009df97ef4f3c27967b2b0b640874f48f..14cdd9dd2cc4ccf1f968dc814e42e3f373b8fdd0 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID7464_GeneralRegionOfInterestMeasurementModifiers
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:35 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:12 by J. Riesmeier
  *
  */
 
index 2d38e5545b8848bb2f84414613d866416ae19713..f71d08601ef0233c19dbfa6388ec4a64ae37c7aa 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file for class CID7469_GenericIntensityAndSizeMeasurements
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:37 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:14 by J. Riesmeier
  *
  */
 
@@ -348,6 +348,12 @@ class DCMTK_CMR_EXPORT CID7469_GenericIntensityAndSizeMeasurements
         WaterFraction,
         /// (130086,DCM,"Relative Linear Stopping Power"), included from CID 7180
         RelativeLinearStoppingPower,
+        /// (130402,DCM,"Class activation"), included from CID 217
+        ClassActivation,
+        /// (130403,DCM,"Gradient-weighted class activation"), included from CID 217
+        GradientWeightedClassActivation,
+        /// (130404,DCM,"Saliency"), included from CID 217
+        Saliency,
         /// (410668003,SCT,"Length"), included from CID 7470
         Length,
         /// (121211,DCM,"Path length"), included from CID 7470
@@ -380,6 +386,8 @@ class DCMTK_CMR_EXPORT CID7469_GenericIntensityAndSizeMeasurements
         DiameterOfCircumscribedCircle,
         /// (121207,DCM,"Height"), included from CID 7470
         Height,
+        /// (121227,DCM,"Line segment length"), included from CID 7470
+        LineSegmentLength,
         /// (L0JK,IBSI,"Maximum 3D Diameter of a Mesh"), included from CID 7470
         Maximum3DDiameterOfAMesh,
         /// (TDIC,IBSI,"Major Axis in 3D Length"), included from CID 7470
index 21a284a3d4f4c0a2cd133d0b3324865fdd1c3e24..1b3cba5401d5963ffc228d73b6659a6a3df70144 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file with DICOM Controlled Terminology Code Definitions (Coding Scheme "DCM", Version "01")
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 16:52:41 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 10:55:18 by J. Riesmeier
  *
  */
 
@@ -34,8 +34,8 @@
  *  code definitions  *
  *--------------------*/
 
-// total number of codes: 4218
-// - retired: 194
+// total number of codes: 4387
+// - retired: 199
 // - no name: 27
 // - not unique: 17
 
@@ -70,6 +70,7 @@
 #define CODE_DCM_RETIRED_DigitalFluoroscopy                                DSRBasicCodedEntry("DF", "DCM", "Digital fluoroscopy")
 #define CODE_DCM_Diaphanography                                            DSRBasicCodedEntry("DG", "DCM", "Diaphanography")
 #define CODE_DCM_RETIRED_DigitalMicroscopy                                 DSRBasicCodedEntry("DM", "DCM", "Digital microscopy")
+#define CODE_DCM_Dermoscopy                                                DSRBasicCodedEntry("DMS", "DCM", "Dermoscopy")
 #define CODE_DCM_Document_DOC                                              DSRBasicCodedEntry("DOC", "DCM", "Document")
 #define CODE_DCM_DocumentDigitizerEquipment                                DSRBasicCodedEntry("DOCD", "DCM", "Document Digitizer Equipment")
 #define CODE_DCM_RETIRED_DigitalSubtractionAngiography                     DSRBasicCodedEntry("DS", "DCM", "Digital Subtraction Angiography")
@@ -77,6 +78,9 @@
 #define CODE_DCM_DigitalRadiography                                        DSRBasicCodedEntry("DX", "DCM", "Digital Radiography")
 #define CODE_DCM_RETIRED_Echocardiography                                  DSRBasicCodedEntry("EC", "DCM", "Echocardiography")
 #define CODE_DCM_Electrocardiography                                       DSRBasicCodedEntry("ECG", "DCM", "Electrocardiography")
+#define CODE_DCM_Electroencephalography                                    DSRBasicCodedEntry("EEG", "DCM", "Electroencephalography")
+#define CODE_DCM_Electromyography                                          DSRBasicCodedEntry("EMG", "DCM", "Electromyography")
+#define CODE_DCM_Electrooculography                                        DSRBasicCodedEntry("EOG", "DCM", "Electrooculography")
 #define CODE_DCM_CardiacElectrophysiology                                  DSRBasicCodedEntry("EPS", "DCM", "Cardiac Electrophysiology")
 #define CODE_DCM_Endoscopy                                                 DSRBasicCodedEntry("ES", "DCM", "Endoscopy")
 #define CODE_DCM_Female                                                    DSRBasicCodedEntry("F", "DCM", "Female")
 #define CODE_DCM_OpticalSurfaceScanner                                     DSRBasicCodedEntry("OSS", "DCM", "Optical Surface Scanner")
 #define CODE_DCM_OtherModality                                             DSRBasicCodedEntry("OT", "DCM", "Other Modality")
 #define CODE_DCM_Plan                                                      DSRBasicCodedEntry("PLAN", "DCM", "Plan")
+#define CODE_DCM_PositionSensor                                            DSRBasicCodedEntry("POS", "DCM", "Position Sensor")
 #define CODE_DCM_PresentationState                                         DSRBasicCodedEntry("PR", "DCM", "Presentation State")
 #define CODE_DCM_HardCopyPrintServer                                       DSRBasicCodedEntry("PRINT", "DCM", "Hard Copy Print Server")
 #define CODE_DCM_PositronEmissionTomography                                DSRBasicCodedEntry("PT", "DCM", "Positron emission tomography")
 #define CODE_DCM_SubjectiveRefraction                                      DSRBasicCodedEntry("SRF", "DCM", "Subjective Refraction")
 #define CODE_DCM_RETIRED_SinglePhotonEmissionComputedTomography            DSRBasicCodedEntry("ST", "DCM", "Single-photon emission computed tomography")
 #define CODE_DCM_AutomatedSlideStainer                                     DSRBasicCodedEntry("STAIN", "DCM", "Automated Slide Stainer")
+#define CODE_DCM_TextureMap                                                DSRBasicCodedEntry("TEXTUREMAP", "DCM", "Texture Map")
 #define CODE_DCM_Thermography                                              DSRBasicCodedEntry("TG", "DCM", "Thermography")
 #define CODE_DCM_UnknownSex                                                DSRBasicCodedEntry("U", "DCM", "Unknown Sex")
 #define CODE_DCM_Unavailable                                               DSRBasicCodedEntry("UNAVAILABLE", "DCM", "Unavailable")
 #define CODE_DCM_ImageOrientation_Patient_ColumnZ                          DSRBasicCodedEntry("110909", "DCM", "Image Orientation (Patient) Column Z")
 #define CODE_DCM_PixelDataRows                                             DSRBasicCodedEntry("110910", "DCM", "Pixel Data Rows")
 #define CODE_DCM_PixelDataColumns                                          DSRBasicCodedEntry("110911", "DCM", "Pixel Data Columns")
+#define CODE_DCM_AlgorithmFamily                                           DSRBasicCodedEntry("111000", "DCM", "Algorithm Family")
 #define CODE_DCM_AlgorithmName                                             DSRBasicCodedEntry("111001", "DCM", "Algorithm Name")
 #define CODE_DCM_AlgorithmParameters                                       DSRBasicCodedEntry("111002", "DCM", "Algorithm Parameters")
 #define CODE_DCM_AlgorithmVersion                                          DSRBasicCodedEntry("111003", "DCM", "Algorithm Version")
 #define CODE_DCM_GreaterThan1YearAgo                                       DSRBasicCodedEntry("111398", "DCM", "> 1 year ago")
 #define CODE_DCM_TimeframeUncertain                                        DSRBasicCodedEntry("111399", "DCM", "Timeframe uncertain")
 #define CODE_DCM_BreastImagingReport                                       DSRBasicCodedEntry("111400", "DCM", "Breast Imaging Report")
-#define CODE_DCM_ReasonForProcedure                                        DSRBasicCodedEntry("111401", "DCM", "Reason for procedure")
+#define CODE_DCM_RETIRED_ReasonForProcedure                                DSRBasicCodedEntry("111401", "DCM", "Reason for Procedure")
 #define CODE_DCM_ClinicalFinding                                           DSRBasicCodedEntry("111402", "DCM", "Clinical Finding")
 #define CODE_DCM_BaselineScreeningMammogram                                DSRBasicCodedEntry("111403", "DCM", "Baseline screening mammogram")
 #define CODE_DCM_FirstMammogramEver                                        DSRBasicCodedEntry("111404", "DCM", "First mammogram ever")
 #define CODE_DCM_NumberOfSimilarFindings                                   DSRBasicCodedEntry("111406", "DCM", "Number of similar findings")
 #define CODE_DCM_ImplantFinding                                            DSRBasicCodedEntry("111407", "DCM", "Implant finding")
 #define CODE_DCM_FilmScreenMammography                                     DSRBasicCodedEntry("111408", "DCM", "Film Screen Mammography")
-#define CODE_DCM_DigitalMammography                                        DSRBasicCodedEntry("111409", "DCM", "Digital Mammography")
+#define CODE_DCM_RETIRED_DigitalMammography                                DSRBasicCodedEntry("111409", "DCM", "Digital Mammography")
 #define CODE_DCM_SurgicalConsult                                           DSRBasicCodedEntry("111410", "DCM", "Surgical consult")
 #define CODE_DCM_MammographyCAD                                            DSRBasicCodedEntry("111411", "DCM", "Mammography CAD")
 #define CODE_DCM_NarrativeSummary                                          DSRBasicCodedEntry("111412", "DCM", "Narrative Summary")
 #define CODE_DCM_PoorlyDemarcated                                          DSRBasicCodedEntry("112141", "DCM", "Poorly demarcated")
 #define CODE_DCM_RETIRED_Circumscribed                                     DSRBasicCodedEntry("112142", "DCM", "Circumscribed")
 #define CODE_DCM_Air                                                       DSRBasicCodedEntry("112143", "DCM", "Air")
-#define CODE_DCM_SoftTissue                                                DSRBasicCodedEntry("112144", "DCM", "Soft tissue")
+#define CODE_DCM_RETIRED_SoftTissue                                        DSRBasicCodedEntry("112144", "DCM", "Soft tissue")
 #define CODE_DCM_Calcium                                                   DSRBasicCodedEntry("112145", "DCM", "Calcium")
 #define CODE_DCM_Acinar                                                    DSRBasicCodedEntry("112146", "DCM", "Acinar")
 #define CODE_DCM_AirSpace                                                  DSRBasicCodedEntry("112147", "DCM", "Air space")
 #define CODE_DCM_CTDIvolNotificationValue                                  DSRBasicCodedEntry("113912", "DCM", "CTDIvol Notification Value")
 #define CODE_DCM_DLPForwardEstimate                                        DSRBasicCodedEntry("113913", "DCM", "DLP Forward Estimate")
 #define CODE_DCM_CTDIvolForwardEstimate                                    DSRBasicCodedEntry("113914", "DCM", "CTDIvol Forward Estimate")
+#define CODE_DCM_AlternativeDoseAlertBehaviorActive                        DSRBasicCodedEntry("113915", "DCM", "Alternative dose alert behavior active")
 #define CODE_DCM_RadiationExposure                                         DSRBasicCodedEntry("113921", "DCM", "Radiation Exposure")
 #define CODE_DCM_RETIRED_RadioactiveSubstanceAdministered                  DSRBasicCodedEntry("113922", "DCM", "Radioactive Substance Administered")
 #define CODE_DCM_RETIRED_RadiationExposureAndProtectionInformation         DSRBasicCodedEntry("113923", "DCM", "Radiation Exposure and Protection Information")
-#define CODE_DCM_SizeSpecificDoseEstimation                                DSRBasicCodedEntry("113930", "DCM", "Size Specific Dose Estimation")
+#define CODE_DCM_SizeSpecificDoseEstimate                                  DSRBasicCodedEntry("113930", "DCM", "Size Specific Dose Estimate")
 #define CODE_DCM_MeasuredLateralDimension                                  DSRBasicCodedEntry("113931", "DCM", "Measured Lateral Dimension")
 #define CODE_DCM_MeasuredAPDimension                                       DSRBasicCodedEntry("113932", "DCM", "Measured AP Dimension")
 #define CODE_DCM_DerivedEffectiveDiameter                                  DSRBasicCodedEntry("113933", "DCM", "Derived Effective Diameter")
 #define CODE_DCM_SeriesOrInstanceUsedForWaterEquivalentDiameterEstimation  DSRBasicCodedEntry("113985", "DCM", "Series or Instance used for Water Equivalent Diameter estimation")
 #define CODE_DCM_ZValueOfLocationOfWaterEquivalentDiameterEstimation       DSRBasicCodedEntry("113986", "DCM", "Z value of location of Water Equivalent Diameter estimation")
 #define CODE_DCM_AAPM220                                                   DSRBasicCodedEntry("113987", "DCM", "AAPM 220")
+#define CODE_DCM_EstimatedFromWaterEquivalentDiameter                      DSRBasicCodedEntry("113988", "DCM", "Estimated from Water Equivalent Diameter")
+#define CODE_DCM_ArithmeticAverageOfSSDEz                                  DSRBasicCodedEntry("113989", "DCM", "Arithmetic Average of SSDE(z)")
+#define CODE_DCM_ArithmeticAverageOfDwz                                    DSRBasicCodedEntry("113990", "DCM", "Arithmetic Average of Dw(z)")
+#define CODE_DCM_DwConversionFactorCoefficients                            DSRBasicCodedEntry("113991", "DCM", "Dw Conversion Factor Coefficients")
+#define CODE_DCM_WaterEquivalentDiameterFromLimitedFOVImages               DSRBasicCodedEntry("113992", "DCM", "Water Equivalent Diameter From Limited FOV Images")
+#define CODE_DCM_SizeSpecificDoseEstimateAtLongitudinalPositionZ           DSRBasicCodedEntry("113993", "DCM", "Size Specific Dose Estimate At Longitudinal Position Z")
+#define CODE_DCM_LongitudinalPositionZ                                     DSRBasicCodedEntry("113994", "DCM", "Longitudinal Position Z")
+#define CODE_DCM_WaterEquivalentDiameterAtLongitudinalPositionZ            DSRBasicCodedEntry("113995", "DCM", "Water Equivalent Diameter At Longitudinal Position Z")
 #define CODE_DCM_NotANumber                                                DSRBasicCodedEntry("114000", "DCM", "Not a number")
 #define CODE_DCM_NegativeInfinity                                          DSRBasicCodedEntry("114001", "DCM", "Negative Infinity")
 #define CODE_DCM_PositiveInfinity                                          DSRBasicCodedEntry("114002", "DCM", "Positive Infinity")
 #define CODE_DCM_IterativeClosestPoint                                     DSRBasicCodedEntry("114213", "DCM", "Iterative Closest Point")
 #define CODE_DCM_Freehand                                                  DSRBasicCodedEntry("114215", "DCM", "Freehand")
 #define CODE_DCM_Checkerboard                                              DSRBasicCodedEntry("114216", "DCM", "Checkerboard")
+#define CODE_DCM_DeviceDescription                                         DSRBasicCodedEntry("120999", "DCM", "Device Description")
+#define CODE_DCM_UniqueDeviceIdentifiers                                   DSRBasicCodedEntry("121000", "DCM", "Unique Device Identifiers")
 #define CODE_DCM_QuotationMode                                             DSRBasicCodedEntry("121001", "DCM", "Quotation Mode")
 #define CODE_DCM_QuotedSource                                              DSRBasicCodedEntry("121002", "DCM", "Quoted Source")
 #define CODE_DCM_Document_121003                                           DSRBasicCodedEntry("121003", "DCM", "Document")
 #define CODE_DCM_ProcedureReported                                         DSRBasicCodedEntry("121058", "DCM", "Procedure reported")
 #define CODE_DCM_RETIRED_PresenceUndetermined                              DSRBasicCodedEntry("121059", "DCM", "Presence Undetermined")
 #define CODE_DCM_RETIRED_History                                           DSRBasicCodedEntry("121060", "DCM", "History")
+#define CODE_DCM_DeviceObserverManufacturerClassUID                        DSRBasicCodedEntry("121061", "DCM", "Device Observer Manufacturer Class UID")
 #define CODE_DCM_RETIRED_Request                                           DSRBasicCodedEntry("121062", "DCM", "Request")
 #define CODE_DCM_RETIRED_CurrentProcedureDescriptions                      DSRBasicCodedEntry("121064", "DCM", "Current Procedure Descriptions")
 #define CODE_DCM_ProcedureDescription                                      DSRBasicCodedEntry("121065", "DCM", "Procedure Description")
 #define CODE_DCM_VolumeOfCircumscribedSphere                               DSRBasicCodedEntry("121220", "DCM", "Volume of circumscribed sphere")
 #define CODE_DCM_VolumeOfEllipsoid                                         DSRBasicCodedEntry("121221", "DCM", "Volume of ellipsoid")
 #define CODE_DCM_VolumeOfSphere                                            DSRBasicCodedEntry("121222", "DCM", "Volume of sphere")
+#define CODE_DCM_ArmOfAngle                                                DSRBasicCodedEntry("121223", "DCM", "Arm of angle")
+#define CODE_DCM_AcetabularAngle                                           DSRBasicCodedEntry("121224", "DCM", "Acetabular angle")
+#define CODE_DCM_Vector                                                    DSRBasicCodedEntry("121225", "DCM", "Vector")
+#define CODE_DCM_ApproximateSpatialLocation                                DSRBasicCodedEntry("121226", "DCM", "Approximate spatial location")
+#define CODE_DCM_LineSegmentLength                                         DSRBasicCodedEntry("121227", "DCM", "Line segment length")
 #define CODE_DCM_PathVertex                                                DSRBasicCodedEntry("121230", "DCM", "Path Vertex")
 #define CODE_DCM_VolumeSurface                                             DSRBasicCodedEntry("121231", "DCM", "Volume Surface")
 #define CODE_DCM_SourceSeriesForSegmentation                               DSRBasicCodedEntry("121232", "DCM", "Source series for segmentation")
 #define CODE_DCM_ContrastBolusIngredientOpaque                             DSRBasicCodedEntry("121381", "DCM", "Contrast/Bolus Ingredient Opaque")
 #define CODE_DCM_QuantityAdministered                                      DSRBasicCodedEntry("121382", "DCM", "Quantity administered")
 #define CODE_DCM_MassAdministered                                          DSRBasicCodedEntry("121383", "DCM", "Mass administered")
+#define CODE_DCM_RTPlanLabel                                               DSRBasicCodedEntry("121384", "DCM", "RT Plan Label")
+#define CODE_DCM_CurrentFractionNumber                                     DSRBasicCodedEntry("121385", "DCM", "Current Fraction Number")
+#define CODE_DCM_NumberOfFractionsPlanned                                  DSRBasicCodedEntry("121386", "DCM", "Number of Fractions Planned")
+#define CODE_DCM_NumberOfFractionsCompleted                                DSRBasicCodedEntry("121387", "DCM", "Number of Fractions Completed")
+#define CODE_DCM_CheckedInStatus                                           DSRBasicCodedEntry("121388", "DCM", "Checked-In Status")
+#define CODE_DCM_ReferencedBeamNumber                                      DSRBasicCodedEntry("121389", "DCM", "Referenced Beam Number")
 #define CODE_DCM_Derivation                                                DSRBasicCodedEntry("121401", "DCM", "Derivation")
 #define CODE_DCM_Normality                                                 DSRBasicCodedEntry("121402", "DCM", "Normality")
 #define CODE_DCM_LevelOfSignificance                                       DSRBasicCodedEntry("121403", "DCM", "Level of Significance")
 #define CODE_DCM_CorrectedSinusNodeRecoveryTime                            DSRBasicCodedEntry("122237", "DCM", "Corrected Sinus Node Recovery Time")
 #define CODE_DCM_MaxVolumeNormalizedTo50mmHgPulsePressure                  DSRBasicCodedEntry("122238", "DCM", "Max volume normalized to 50mmHg pulse pressure")
 #define CODE_DCM_OxygenConsumption                                         DSRBasicCodedEntry("122239", "DCM", "Oxygen Consumption")
-#define CODE_DCM_122240                                                    DSRBasicCodedEntry("122240", "DCM", "BSA = 3.207*WT^(0.7285-0.0188 log (WT)) *HT^0.3")
-#define CODE_DCM_122241                                                    DSRBasicCodedEntry("122241", "DCM", "BSA = 0.007184*WT^ 0.425*HT^0.725")
-#define CODE_DCM_122242                                                    DSRBasicCodedEntry("122242", "DCM", "BSA = 0.0235*WT^0.51456*HT^ 0.42246")
+#define CODE_DCM_122240                                                    DSRBasicCodedEntry("122240", "DCM", "BSA = 0.003207*WT^(0.7285-0.0188*log(WT))*HT^0.3")
+#define CODE_DCM_122241                                                    DSRBasicCodedEntry("122241", "DCM", "BSA = 0.007184*WT^0.425*HT^0.725")
+#define CODE_DCM_122242                                                    DSRBasicCodedEntry("122242", "DCM", "BSA = 0.0235*WT^0.51456*HT^0.42246")
 #define CODE_DCM_122243                                                    DSRBasicCodedEntry("122243", "DCM", "BSA = 0.024265*WT^0.5378*HT^0.3964")
-#define CODE_DCM_122244                                                    DSRBasicCodedEntry("122244", "DCM", "BSA = (HT * WT/36) ^0.5")
+#define CODE_DCM_122244                                                    DSRBasicCodedEntry("122244", "DCM", "BSA = (HT*WT/36)^0.5")
 #define CODE_DCM_122245                                                    DSRBasicCodedEntry("122245", "DCM", "BSA = 1321+0.3433*WT")
-#define CODE_DCM_122246                                                    DSRBasicCodedEntry("122246", "DCM", "BSA = 0.0004688 * WT ^ (0.8168 - 0.0154 * log(WT))")
+#define CODE_DCM_122246                                                    DSRBasicCodedEntry("122246", "DCM", "BSA = 0.0004688*WT^(0.8168-0.0154*log(WT))")
 #define CODE_DCM_122247                                                    DSRBasicCodedEntry("122247", "DCM", "VO2male = BSA (138.1 - 11.49 * loge(age) + 0.378 * HRf)")
 #define CODE_DCM_122248                                                    DSRBasicCodedEntry("122248", "DCM", "VO2female = BSA (138.1 - 17.04 * loge(age) + 0.378 * HRf)")
 #define CODE_DCM_122249                                                    DSRBasicCodedEntry("122249", "DCM", "VO2 = VeSTPD * 10 * (FIO2 - FE02)")
 #define CODE_DCM_122262                                                    DSRBasicCodedEntry("122262", "DCM", "Area = Flow / 44.5 * sqrt(Gradient[mmHg])")
 #define CODE_DCM_122263                                                    DSRBasicCodedEntry("122263", "DCM", "MVA = Flow / 38.0 * sqrt(Gradient[mmHg])")
 #define CODE_DCM_122265                                                    DSRBasicCodedEntry("122265", "DCM", "BMI = Wt / Ht ^ 2")
-#define CODE_DCM_122266                                                    DSRBasicCodedEntry("122266", "DCM", "BSA = 0.007358 * WT ^ 0.425 * HT ^ 0.725")
-#define CODE_DCM_122267                                                    DSRBasicCodedEntry("122267", "DCM", "BSA = 0.010265 * WT ^ 0.423 * HT ^ 0.651")
-#define CODE_DCM_122268                                                    DSRBasicCodedEntry("122268", "DCM", "BSA = 0.008883 * WT ^ 0.444 * HT ^ 0.663")
-#define CODE_DCM_122269                                                    DSRBasicCodedEntry("122269", "DCM", "BSA = 0.038189 * WT ^ 0.423 * HT ^ 0.362")
-#define CODE_DCM_122270                                                    DSRBasicCodedEntry("122270", "DCM", "BSA = 0.009568 * WT ^ 0.473 * HT ^ 0.655")
+#define CODE_DCM_122266                                                    DSRBasicCodedEntry("122266", "DCM", "BSA = 0.007358*WT^0.425*HT^0.725")
+#define CODE_DCM_122267                                                    DSRBasicCodedEntry("122267", "DCM", "BSA = 0.010265*WT^0.423*HT^0.651")
+#define CODE_DCM_122268                                                    DSRBasicCodedEntry("122268", "DCM", "BSA = 0.008883*WT^0.444*HT^0.663")
+#define CODE_DCM_122269                                                    DSRBasicCodedEntry("122269", "DCM", "BSA = 0.038189*WT^0.423*HT^0.362")
+#define CODE_DCM_122270                                                    DSRBasicCodedEntry("122270", "DCM", "BSA = 0.009568*WT^0.473*HT^0.655")
 #define CODE_DCM_SkinConditionWarm                                         DSRBasicCodedEntry("122271", "DCM", "Skin Condition Warm")
 #define CODE_DCM_SkinConditionCool                                         DSRBasicCodedEntry("122272", "DCM", "Skin Condition Cool")
 #define CODE_DCM_SkinConditionCold                                         DSRBasicCodedEntry("122273", "DCM", "Skin Condition Cold")
 #define CODE_DCM_FrameToFrameAnalysis                                      DSRBasicCodedEntry("122499", "DCM", "Frame to Frame Analysis")
 #define CODE_DCM_AreaOfClosedIrregularPolygon                              DSRBasicCodedEntry("122501", "DCM", "Area of closed irregular polygon")
 #define CODE_DCM_AreaOfAClosedNURBS                                        DSRBasicCodedEntry("122502", "DCM", "Area of a closed NURBS")
-#define CODE_DCM_IntegrationOfSumOfClosedAreasonContiguousSlices           DSRBasicCodedEntry("122503", "DCM", "Integration of sum of closed areas on contiguous slices")
+#define CODE_DCM_IntegrationOfSumOfClosedAreasonContiguousSlicesMethodForVolume DSRBasicCodedEntry("122503", "DCM", "Integration of sum of closed areas on contiguous slices method for volume")
 #define CODE_DCM_Calibration                                               DSRBasicCodedEntry("122505", "DCM", "Calibration")
 #define CODE_DCM_LeftContour                                               DSRBasicCodedEntry("122507", "DCM", "Left Contour")
 #define CODE_DCM_RightContour                                              DSRBasicCodedEntry("122508", "DCM", "Right Contour")
 #define CODE_DCM_AcquisitionEquipmentAlignment                             DSRBasicCodedEntry("125023", "DCM", "Acquisition Equipment Alignment")
 #define CODE_DCM_ImageContentBasedAlignment                                DSRBasicCodedEntry("125024", "DCM", "Image Content-based Alignment")
 #define CODE_DCM_VisualAlignment                                           DSRBasicCodedEntry("125025", "DCM", "Visual Alignment")
+#define CODE_DCM_ImageContentAndFiducialBasedAlignment                     DSRBasicCodedEntry("125026", "DCM", "Image Content and Fiducial Based Alignment")
+#define CODE_DCM_DeformedForRegistration                                   DSRBasicCodedEntry("125027", "DCM", "Deformed for Registration")
+#define CODE_DCM_SourceDeformableSpatialRegistration                       DSRBasicCodedEntry("125028", "DCM", "Source Deformable Spatial Registration")
 #define CODE_DCM_InterHemisphericPlane                                     DSRBasicCodedEntry("125030", "DCM", "Inter-Hemispheric Plane")
 #define CODE_DCM_RightHemisphereMostAnterior                               DSRBasicCodedEntry("125031", "DCM", "Right Hemisphere Most Anterior")
 #define CODE_DCM_RightHemisphereMostPosterior                              DSRBasicCodedEntry("125032", "DCM", "Right Hemisphere Most Posterior")
 #define CODE_DCM_LeftHemisphereMostInferior                                DSRBasicCodedEntry("125038", "DCM", "Left Hemisphere Most Inferior")
 #define CODE_DCM_Background                                                DSRBasicCodedEntry("125040", "DCM", "Background")
 #define CODE_DCM_RegistrationInput                                         DSRBasicCodedEntry("125041", "DCM", "Registration Input")
-#define CODE_DCM_VascularUltrasoundProcedureReport                         DSRBasicCodedEntry("125100", "DCM", "Vascular Ultrasound Procedure Report")
+#define CODE_DCM_RETIRED_VascularUltrasoundProcedureReport                 DSRBasicCodedEntry("125100", "DCM", "Vascular Ultrasound Procedure Report")
 #define CODE_DCM_VesselBranch                                              DSRBasicCodedEntry("125101", "DCM", "Vessel Branch")
 #define CODE_DCM_GraftType                                                 DSRBasicCodedEntry("125102", "DCM", "Graft Type")
 #define CODE_DCM_MeasurementOrientation                                    DSRBasicCodedEntry("125105", "DCM", "Measurement Orientation")
 #define CODE_DCM_MultiparametricMRI                                        DSRBasicCodedEntry("126020", "DCM", "Multiparametric MRI")
 #define CODE_DCM_MultiparametricMRIOfProstate                              DSRBasicCodedEntry("126021", "DCM", "Multiparametric MRI of prostate")
 #define CODE_DCM_MultiparametricMRIOfWholeBody                             DSRBasicCodedEntry("126022", "DCM", "Multiparametric MRI of whole body")
-#define CODE_DCM_SumOfSegmentedVoxelVolumes                                DSRBasicCodedEntry("126030", "DCM", "Sum of segmented voxel volumes")
+#define CODE_DCM_LWHMethodForVolumeOfEllipsoid                             DSRBasicCodedEntry("126029", "DCM", "LWH method for volume of ellipsoid")
+#define CODE_DCM_SumOfSegmentedVoxelMethodForVolume                        DSRBasicCodedEntry("126030", "DCM", "Sum of segmented voxel method for volume")
 #define CODE_DCM_PeakValueWithinROI                                        DSRBasicCodedEntry("126031", "DCM", "Peak Value Within ROI")
 #define CODE_DCM_MetabolicVolume                                           DSRBasicCodedEntry("126032", "DCM", "Metabolic Volume")
 #define CODE_DCM_TotalLesionGlycolysis                                     DSRBasicCodedEntry("126033", "DCM", "Total Lesion Glycolysis")
 #define CODE_DCM_Florbetaben_F18                                           DSRBasicCodedEntry("126501", "DCM", "Florbetaben F^18^")
 #define CODE_DCM_T807_F18                                                  DSRBasicCodedEntry("126502", "DCM", "T807 F^18^")
 #define CODE_DCM_Flubatine_F18                                             DSRBasicCodedEntry("126503", "DCM", "Flubatine F^18^")
+#define CODE_DCM_Lutetium177NAcetylaspartylglutamate                       DSRBasicCodedEntry("126509", "DCM", "Lutetium^177^ n-acetylaspartylglutamate")
 #define CODE_DCM_MonoclonalAntibody_mAb_64Cu                               DSRBasicCodedEntry("126510", "DCM", "Monoclonal Antibody (mAb) ^64^Cu")
 #define CODE_DCM_MonoclonalAntibody_mAb_89Zr                               DSRBasicCodedEntry("126511", "DCM", "Monoclonal Antibody (mAb) ^89^Zr")
 #define CODE_DCM_Trastuzumab_89Zr                                          DSRBasicCodedEntry("126512", "DCM", "Trastuzumab ^89^Zr")
 #define CODE_DCM_DfFKPEG3_89Zr                                             DSRBasicCodedEntry("126761", "DCM", "Df-FK-PEG(3) ^89^Zr")
 #define CODE_DCM_DfFK2_89Zr                                                DSRBasicCodedEntry("126762", "DCM", "Df-[FK](2) ^89^Zr")
 #define CODE_DCM_DfFK23PEG4_89Zr                                           DSRBasicCodedEntry("126763", "DCM", "Df-[FK](2)-3PEG(4) ^89^Zr")
-#define CODE_DCM_IEC61217PatientSupportContinuousAngle                     DSRBasicCodedEntry("126801", "DCM", "IEC61217 Patient Support Continuous Angle")
+#define CODE_DCM_Iodinated_I125DPA713                                      DSRBasicCodedEntry("126764", "DCM", "Iodinated I^125^ DPA-713")
+#define CODE_DCM_DPA713_11C                                                DSRBasicCodedEntry("126765", "DCM", "DPA-713 ^11^C")
+#define CODE_DCM_DPA714_18F                                                DSRBasicCodedEntry("126766", "DCM", "DPA-714 ^18^F")
+#define CODE_DCM_IEC61217PatientSupportContinuousYawAngle                  DSRBasicCodedEntry("126801", "DCM", "IEC61217 Patient Support Continuous Yaw Angle")
 #define CODE_DCM_IEC61217TableTopContinuousPitchAngle                      DSRBasicCodedEntry("126802", "DCM", "IEC61217 Table Top Continuous Pitch Angle")
 #define CODE_DCM_IEC61217TableTopContinuousRollAngle                       DSRBasicCodedEntry("126803", "DCM", "IEC61217 Table Top Continuous Roll Angle")
 #define CODE_DCM_IEC61217TableTopEccentricAxisDistance                     DSRBasicCodedEntry("126804", "DCM", "IEC61217 Table Top Eccentric Axis Distance")
 #define CODE_DCM_MouseAlphaSynucleinPreformedFibrils                       DSRBasicCodedEntry("127852", "DCM", "Mouse alpha synuclein preformed fibrils")
 #define CODE_DCM_HumanTauPreformedFibrils                                  DSRBasicCodedEntry("127853", "DCM", "Human Tau preformed fibrils")
 #define CODE_DCM_MouseTauPreformedFibrils                                  DSRBasicCodedEntry("127854", "DCM", "Mouse Tau preformed fibrils")
-#define CODE_DCM_NonIonicIodinatedContrastAgent                            DSRBasicCodedEntry("127855", "DCM", "Non-ionic iodinated contrast agent")
+#define CODE_DCM_RETIRED_NonIonicIodinatedContrastAgent                    DSRBasicCodedEntry("127855", "DCM", "Non-ionic iodinated contrast agent")
 #define CODE_DCM_HeartValveFlail                                           DSRBasicCodedEntry("127856", "DCM", "Heart valve flail")
 #define CODE_DCM_GlucoseMeasurementDate                                    DSRBasicCodedEntry("127857", "DCM", "Glucose Measurement Date")
 #define CODE_DCM_GlucoseMeasurementTime                                    DSRBasicCodedEntry("127858", "DCM", "Glucose Measurement Time")
 #define CODE_DCM_AdverseEventDetectionDateTime                             DSRBasicCodedEntry("130215", "DCM", "Adverse Event Detection DateTime")
 #define CODE_DCM_ReferencedImagingAgentAdministrationStepUID               DSRBasicCodedEntry("130216", "DCM", "Referenced Imaging Agent Administration Step UID")
 #define CODE_DCM_ReferencedImagingAgentAdministrationPhaseIdentifier       DSRBasicCodedEntry("130217", "DCM", "Referenced Imaging Agent Administration Phase Identifier")
-#define CODE_DCM_ProgrammableDevice                                        DSRBasicCodedEntry("130218", "DCM", "Programmable Device")
+#define CODE_DCM_ProgrammableInjectorDevice                                DSRBasicCodedEntry("130218", "DCM", "Programmable Injector Device")
 #define CODE_DCM_NumberOfInjectorHeads                                     DSRBasicCodedEntry("130219", "DCM", "Number of Injector Heads")
 #define CODE_DCM_AdministrationDiscontinued                                DSRBasicCodedEntry("130220", "DCM", "Administration discontinued")
 #define CODE_DCM_ImagingAgentVolumePerUnitOfPresentation                   DSRBasicCodedEntry("130221", "DCM", "Imaging Agent Volume per Unit of Presentation")
 #define CODE_DCM_ImagingAgentAdministrationInjectorEventType               DSRBasicCodedEntry("130234", "DCM", "Imaging Agent Administration Injector Event Type")
 #define CODE_DCM_InjectorEventDetectionDateTime                            DSRBasicCodedEntry("130235", "DCM", "Injector Event Detection DateTime")
 #define CODE_DCM_PlannedImagingAgentAdministrationSOPInstance              DSRBasicCodedEntry("130236", "DCM", "Planned Imaging Agent Administration SOP Instance")
-#define CODE_DCM_ImagingAgentAdministrationSyringePumpPhaseActivity        DSRBasicCodedEntry("130237", "DCM", "Imaging Agent Administration Syringe/Pump Phase Activity")
+#define CODE_DCM_ImagingAgentAdministrationActivity                        DSRBasicCodedEntry("130237", "DCM", "Imaging Agent Administration Activity")
 #define CODE_DCM_ImagingAgentComponent                                     DSRBasicCodedEntry("130238", "DCM", "Imaging Agent Component")
 #define CODE_DCM_ComponentVolume                                           DSRBasicCodedEntry("130239", "DCM", "Component Volume")
 #define CODE_DCM_TotalPhaseVolumeAdministered                              DSRBasicCodedEntry("130240", "DCM", "Total Phase Volume Administered")
 #define CODE_DCM_ContrastReactionProphylacticAgent                         DSRBasicCodedEntry("130259", "DCM", "Contrast Reaction Prophylactic Agent")
 #define CODE_DCM_ImagingAgentAdministrationPerformedPhaseUID               DSRBasicCodedEntry("130261", "DCM", "Imaging Agent Administration Performed Phase UID")
 #define CODE_DCM_ReferencedImagingAgentAdministrationPhaseUID              DSRBasicCodedEntry("130262", "DCM", "Referenced Imaging Agent Administration Phase UID")
+#define CODE_DCM_Median                                                    DSRBasicCodedEntry("130290", "DCM", "Median")
 #define CODE_DCM_SkinOfParaspinalAreaOfTheNeck                             DSRBasicCodedEntry("130300", "DCM", "Skin of paraspinal area of the neck")
 #define CODE_DCM_SkinOfParaspinalAreaOfTheSuperiorBack                     DSRBasicCodedEntry("130301", "DCM", "Skin of paraspinal area of the superior back")
 #define CODE_DCM_SkinOfUpperParaspinalRegion                               DSRBasicCodedEntry("130302", "DCM", "Skin of upper paraspinal region")
 #define CODE_DCM_SkinOfUpperAntihelixOfEar                                 DSRBasicCodedEntry("130321", "DCM", "Skin of upper antihelix of ear")
 #define CODE_DCM_SkinOfUpperEyelidMargin                                   DSRBasicCodedEntry("130322", "DCM", "Skin of upper eyelid margin")
 #define CODE_DCM_SkinOfMidBack                                             DSRBasicCodedEntry("130323", "DCM", "Skin of mid back")
+#define CODE_DCM_FunctionalConditionPresentDuringAcquisition               DSRBasicCodedEntry("130324", "DCM", "Functional condition present during acquisition")
+#define CODE_DCM_JawPair                                                   DSRBasicCodedEntry("130330", "DCM", "Jaw Pair")
+#define CODE_DCM_LeafPairs                                                 DSRBasicCodedEntry("130331", "DCM", "Leaf Pairs")
+#define CODE_DCM_VariableCircularCollimator                                DSRBasicCodedEntry("130332", "DCM", "Variable Circular Collimator")
+#define CODE_DCM_SingleLeaves                                              DSRBasicCodedEntry("130333", "DCM", "Single Leaves")
+#define CODE_DCM_XOrientation                                              DSRBasicCodedEntry("130334", "DCM", "X Orientation")
+#define CODE_DCM_YOrientation                                              DSRBasicCodedEntry("130335", "DCM", "Y Orientation")
+#define CODE_DCM_PhysicalCompensator                                       DSRBasicCodedEntry("130340", "DCM", "Physical Compensator")
+#define CODE_DCM_TotalBodyIrradiation                                      DSRBasicCodedEntry("130341", "DCM", "Total Body Irradiation")
+#define CODE_DCM_TotalSkinIrradiation                                      DSRBasicCodedEntry("130342", "DCM", "Total Skin Irradiation")
+#define CODE_DCM_IsocentricPatientSupportContinuousPitchAngle              DSRBasicCodedEntry("126812", "DCM", "Isocentric Patient Support Continuous Pitch Angle")
+#define CODE_DCM_IsocentricPatientSupportContinuousRollAngle               DSRBasicCodedEntry("126813", "DCM", "Isocentric Patient Support Continuous Roll Angle")
+#define CODE_DCM_IsocentricPatientSupportContinuousYawAngle                DSRBasicCodedEntry("126814", "DCM", "Isocentric Patient Support Continuous Yaw Angle")
+#define CODE_DCM_IsocentricPatientSupportLateralPosition                   DSRBasicCodedEntry("126815", "DCM", "Isocentric Patient Support Lateral Position")
+#define CODE_DCM_IsocentricPatientSupportLongitudinalPosition              DSRBasicCodedEntry("126816", "DCM", "Isocentric Patient Support Longitudinal Position")
+#define CODE_DCM_IsocentricPatientSupportVerticalPosition                  DSRBasicCodedEntry("126817", "DCM", "Isocentric Patient Support Vertical Position")
+#define CODE_DCM_ElectronFixedAperture                                     DSRBasicCodedEntry("130343", "DCM", "Electron Fixed Aperture")
+#define CODE_DCM_PhotonFixedAperture                                       DSRBasicCodedEntry("130344", "DCM", "Photon Fixed Aperture")
+#define CODE_DCM_IntraoperativeFixedAperture                               DSRBasicCodedEntry("130345", "DCM", "Intraoperative Fixed Aperture")
+#define CODE_DCM_HardWedge                                                 DSRBasicCodedEntry("130346", "DCM", "Hard Wedge")
+#define CODE_DCM_MotorizedWedge                                            DSRBasicCodedEntry("130347", "DCM", "Motorized Wedge")
+#define CODE_DCM_DynamicWedge                                              DSRBasicCodedEntry("130348", "DCM", "Dynamic Wedge")
+#define CODE_DCM_Graticule                                                 DSRBasicCodedEntry("130349", "DCM", "Graticule")
+#define CODE_DCM_Reticle                                                   DSRBasicCodedEntry("130350", "DCM", "Reticle")
+#define CODE_DCM_ImageDetector                                             DSRBasicCodedEntry("130351", "DCM", "Image Detector")
+#define CODE_DCM_FilmHolder                                                DSRBasicCodedEntry("130352", "DCM", "Film Holder")
+#define CODE_DCM_WinstonLutzPointer                                        DSRBasicCodedEntry("130353", "DCM", "Winston-Lutz Pointer")
+#define CODE_DCM_BowtieFilter                                              DSRBasicCodedEntry("130354", "DCM", "Bowtie Filter")
+#define CODE_DCM_FlatteningFilterBeam                                      DSRBasicCodedEntry("130355", "DCM", "Flattening Filter Beam")
+#define CODE_DCM_NonFlatteningFilterBeam                                   DSRBasicCodedEntry("130356", "DCM", "Non-Flattening Filter Beam")
+#define CODE_DCM_PartialFlatteningFilterBeam                               DSRBasicCodedEntry("130357", "DCM", "Partial Flattening Filter Beam")
+#define CODE_DCM_PhysicsAssistant                                          DSRBasicCodedEntry("128678", "DCM", "Physics Assistant")
+#define CODE_DCM_NominalRadiationSourceLocation                            DSRBasicCodedEntry("130358", "DCM", "Nominal Radiation Source Location")
+#define CODE_DCM_TreatmentMachineIsocenter                                 DSRBasicCodedEntry("130359", "DCM", "Treatment Machine Isocenter")
+#define CODE_DCM_FixedLaserSetupPoint                                      DSRBasicCodedEntry("130360", "DCM", "Fixed Laser Setup Point")
+#define CODE_DCM_RadiotherapyTreatmentDevice                               DSRBasicCodedEntry("130361", "DCM", "Radiotherapy Treatment Device")
+#define CODE_DCM_HeadNodeSet                                               DSRBasicCodedEntry("130362", "DCM", "Head Node Set")
+#define CODE_DCM_BodyNodeSet                                               DSRBasicCodedEntry("130363", "DCM", "Body Node Set")
+#define CODE_DCM_TrigeminalNodeSet                                         DSRBasicCodedEntry("130364", "DCM", "Trigeminal Node Set")
+#define CODE_DCM_QANodePair                                                DSRBasicCodedEntry("130365", "DCM", "QA Node Pair")
+#define CODE_DCM_QANode                                                    DSRBasicCodedEntry("130366", "DCM", "QA Node")
+#define CODE_DCM_RTVRendition                                              DSRBasicCodedEntry("130370", "DCM", "RTV Rendition")
+#define CODE_DCM_RTVAudioAndVideoRendition                                 DSRBasicCodedEntry("130371", "DCM", "RTV Audio and Video Rendition")
+#define CODE_DCM_RTVStereoVideoRendition                                   DSRBasicCodedEntry("130372", "DCM", "RTV Stereo Video Rendition")
+#define CODE_DCM_RTVAudioAndStereoVideoRendition                           DSRBasicCodedEntry("130373", "DCM", "RTV Audio and Stereo Video Rendition")
+#define CODE_DCM_GeometricPurposeOfRegion                                  DSRBasicCodedEntry("130400", "DCM", "Geometric purpose of region")
+#define CODE_DCM_VisualExplanation                                         DSRBasicCodedEntry("130401", "DCM", "Visual explanation")
+#define CODE_DCM_ClassActivation                                           DSRBasicCodedEntry("130402", "DCM", "Class activation")
+#define CODE_DCM_GradientWeightedClassActivation                           DSRBasicCodedEntry("130403", "DCM", "Gradient-weighted class activation")
+#define CODE_DCM_Saliency                                                  DSRBasicCodedEntry("130404", "DCM", "Saliency")
+#define CODE_DCM_PatientAttachedDoseControlObject                          DSRBasicCodedEntry("130405", "DCM", "Patient-Attached Dose Control Object")
+#define CODE_DCM_NonUterineLeiomyosarcoma                                  DSRBasicCodedEntry("130406", "DCM", "Non-uterine leiomyosarcoma")
+#define CODE_DCM_BoneAndSoftTissue                                         DSRBasicCodedEntry("130407", "DCM", "Bone and soft tissue")
+#define CODE_DCM_PerivascularAdiposeTissueFatAttenuationIndex              DSRBasicCodedEntry("130408", "DCM", "Perivascular adipose tissue fat attenuation index")
+#define CODE_DCM_PatientPosition                                           DSRBasicCodedEntry("130410", "DCM", "Patient position")
+#define CODE_DCM_PatientRotationLongitudinal                               DSRBasicCodedEntry("130411", "DCM", "Patient rotation longitudinal")
+#define CODE_DCM_PatientElevation                                          DSRBasicCodedEntry("130412", "DCM", "Patient elevation")
+#define CODE_DCM_HyperventilationBegin                                     DSRBasicCodedEntry("130413", "DCM", "Hyperventilation begin")
+#define CODE_DCM_HyperventilationEnd                                       DSRBasicCodedEntry("130414", "DCM", "Hyperventilation end")
+#define CODE_DCM_PostHyperventilation                                      DSRBasicCodedEntry("130415", "DCM", "Post-hyperventilation")
+#define CODE_DCM_AirflowThermistor                                         DSRBasicCodedEntry("130416", "DCM", "Airflow Thermistor")
+#define CODE_DCM_AirflowThermocouple                                       DSRBasicCodedEntry("130417", "DCM", "Airflow Thermocouple")
+#define CODE_DCM_AirflowNasalProng                                         DSRBasicCodedEntry("130418", "DCM", "Airflow Nasal Prong")
+#define CODE_DCM_AirflowPVDF                                               DSRBasicCodedEntry("130419", "DCM", "Airflow PVDF")
+#define CODE_DCM_AirflowCPAP                                               DSRBasicCodedEntry("130420", "DCM", "Airflow CPAP")
+#define CODE_DCM_Airflow                                                   DSRBasicCodedEntry("130421", "DCM", "Airflow")
+#define CODE_DCM_PAPPressure                                               DSRBasicCodedEntry("130422", "DCM", "PAP Pressure")
+#define CODE_DCM_PAPLeakPressure                                           DSRBasicCodedEntry("130423", "DCM", "PAP Leak Pressure")
+#define CODE_DCM_PAPTidalVolume                                            DSRBasicCodedEntry("130424", "DCM", "PAP Tidal Volume")
+#define CODE_DCM_EsophagealPressure                                        DSRBasicCodedEntry("130425", "DCM", "Esophageal Pressure")
+#define CODE_DCM_RespiratoryPressure                                       DSRBasicCodedEntry("130426", "DCM", "Respiratory Pressure")
+#define CODE_DCM_ThoracicRespiratoryInductance                             DSRBasicCodedEntry("130427", "DCM", "Thoracic Respiratory Inductance")
+#define CODE_DCM_AbdominalRespiratoryInductance                            DSRBasicCodedEntry("130428", "DCM", "Abdominal Respiratory Inductance")
+#define CODE_DCM_ThoracicRespiratoryPVDF                                   DSRBasicCodedEntry("130429", "DCM", "Thoracic Respiratory PVDF")
+#define CODE_DCM_AbdominalRespiratoryPVDF                                  DSRBasicCodedEntry("130430", "DCM", "Abdominal Respiratory PVDF")
+#define CODE_DCM_ThoracicRespiratoryEffort                                 DSRBasicCodedEntry("130431", "DCM", "Thoracic Respiratory Effort")
+#define CODE_DCM_AbdominalRespiratoryEffort                                DSRBasicCodedEntry("130432", "DCM", "Abdominal Respiratory Effort")
+#define CODE_DCM_RespiratoryEffort                                         DSRBasicCodedEntry("130433", "DCM", "Respiratory Effort")
+#define CODE_DCM_CO2Transcutaneous                                         DSRBasicCodedEntry("130434", "DCM", "CO2 Transcutaneous")
+#define CODE_DCM_CO2WaveformEndTidalMainStream                             DSRBasicCodedEntry("130435", "DCM", "CO2 Waveform End-tidal Main-stream")
+#define CODE_DCM_CO2TrendEndTidalMainStream                                DSRBasicCodedEntry("130436", "DCM", "CO2 Trend End-tidal Main-stream")
+#define CODE_DCM_CO2WaveformEndTidalSideStream                             DSRBasicCodedEntry("130437", "DCM", "CO2 Waveform End-tidal Side-stream")
+#define CODE_DCM_CO2TrendEndTidalSideStream                                DSRBasicCodedEntry("130438", "DCM", "CO2 Trend End-tidal Side-stream")
+#define CODE_DCM_CO2WaveformMainStream                                     DSRBasicCodedEntry("130439", "DCM", "CO2 Waveform Main-stream")
+#define CODE_DCM_CO2WaveformSideStream                                     DSRBasicCodedEntry("130440", "DCM", "CO2 Waveform Side-stream")
+#define CODE_DCM_CO2TrendMainStream                                        DSRBasicCodedEntry("130441", "DCM", "CO2 Trend Main-stream")
+#define CODE_DCM_CO2TrendSideStream                                        DSRBasicCodedEntry("130442", "DCM", "CO2 Trend Side-stream")
+#define CODE_DCM_CO2Respiration                                            DSRBasicCodedEntry("130443", "DCM", "CO2 Respiration")
+#define CODE_DCM_RTTreatmentWithAdHocPlanning                              DSRBasicCodedEntry("130444", "DCM", "RT Treatment with Ad Hoc Planning")
+#define CODE_DCM_ImagingAgentAdministrationStepSequenceNumber              DSRBasicCodedEntry("130445", "DCM", "Imaging Agent Administration Step Sequence Number")
+#define CODE_DCM_OperatorDecisionToTerminateTreatment                      DSRBasicCodedEntry("130450", "DCM", "Operator decision to terminate treatment")
+#define CODE_DCM_PatientDecisionToTerminateTreatment                       DSRBasicCodedEntry("130451", "DCM", "Patient decision to terminate treatment")
+#define CODE_DCM_PhysicianDecisionToTerminateTreatment                     DSRBasicCodedEntry("130452", "DCM", "Physician decision to terminate treatment")
+#define CODE_DCM_TreatmentTerminated                                       DSRBasicCodedEntry("130453", "DCM", "Treatment Terminated")
+#define CODE_DCM_ResolvedByOverridingInterlock                             DSRBasicCodedEntry("130454", "DCM", "Resolved by overriding Interlock")
+#define CODE_DCM_ResolvedByRepositioningPatient                            DSRBasicCodedEntry("130455", "DCM", "Resolved by repositioning Patient")
+#define CODE_DCM_BolusPresent                                              DSRBasicCodedEntry("130456", "DCM", "Bolus Present")
+#define CODE_DCM_ConePresent                                               DSRBasicCodedEntry("130457", "DCM", "Cone Present")
+#define CODE_DCM_BlockPresent                                              DSRBasicCodedEntry("130458", "DCM", "Block Present")
+#define CODE_DCM_ApplicatorPresent                                         DSRBasicCodedEntry("130459", "DCM", "Applicator Present")
+#define CODE_DCM_HeadframePresent                                          DSRBasicCodedEntry("130460", "DCM", "Headframe Present")
+#define CODE_DCM_InappropriatePatientOrientation                           DSRBasicCodedEntry("130461", "DCM", "Inappropriate Patient Orientation")
+#define CODE_DCM_InappropriatePatientPosition                              DSRBasicCodedEntry("130462", "DCM", "Inappropriate Patient Position")
+#define CODE_DCM_MachineNotAvailable                                       DSRBasicCodedEntry("130463", "DCM", "Machine Not Available")
+#define CODE_DCM_ChangeInPatientAnatomy                                    DSRBasicCodedEntry("130464", "DCM", "Change in Patient Anatomy")
+#define CODE_DCM_MachineCalibrationAdjustment                              DSRBasicCodedEntry("130465", "DCM", "Machine Calibration Adjustment")
+#define CODE_DCM_UnavailabilityOfABeamModifier                             DSRBasicCodedEntry("130466", "DCM", "Unavailability of a Beam Modifier")
+#define CODE_DCM_MachineCapabilityLicenseExpired                           DSRBasicCodedEntry("130467", "DCM", "Machine Capability License Expired")
+#define CODE_DCM_BeamTargetingToleranceViolation                           DSRBasicCodedEntry("130468", "DCM", "Beam Targeting Tolerance Violation")
+#define CODE_DCM_MetersetToleranceViolation                                DSRBasicCodedEntry("130469", "DCM", "Meterset Tolerance Violation")
+#define CODE_DCM_DeliveryRateToleranceViolation                            DSRBasicCodedEntry("130470", "DCM", "Delivery Rate Tolerance Violation")
+#define CODE_DCM_JawPositionToleranceViolation                             DSRBasicCodedEntry("130471", "DCM", "Jaw Position Tolerance Violation")
+#define CODE_DCM_MLCPositionToleranceViolation                             DSRBasicCodedEntry("130472", "DCM", "MLC Position Tolerance Violation")
+#define CODE_DCM_SourcePositionToleranceViolation                          DSRBasicCodedEntry("130473", "DCM", "Source Position Tolerance Violation")
+#define CODE_DCM_DoseRateToleranceViolation                                DSRBasicCodedEntry("130474", "DCM", "Dose Rate Tolerance Violation")
+#define CODE_DCM_PrimaryFluenceMonitoringSystemInterlock                   DSRBasicCodedEntry("130475", "DCM", "Primary Fluence Monitoring System Interlock")
+#define CODE_DCM_SecondaryFluenceMonitoringSystemInterlock                 DSRBasicCodedEntry("130476", "DCM", "Secondary Fluence Monitoring System Interlock")
+#define CODE_DCM_TimerInterlock                                            DSRBasicCodedEntry("130477", "DCM", "Timer Interlock")
+#define CODE_DCM_DoorInterlock                                             DSRBasicCodedEntry("130478", "DCM", "Door Interlock")
+#define CODE_DCM_PatientMotionInterlock                                    DSRBasicCodedEntry("130479", "DCM", "Patient Motion Interlock")
+#define CODE_DCM_FamilyHistoryOfNonMelanomaSkinCancer                      DSRBasicCodedEntry("130480", "DCM", "Family history of non-melanoma skin cancer")
+#define CODE_DCM_FamilyHistoryOfMelanomaInSitu                             DSRBasicCodedEntry("130481", "DCM", "Family history of melanoma in situ")
+#define CODE_DCM_HistoryOfNonMelanomaSkinCancer                            DSRBasicCodedEntry("130482", "DCM", "History of non-melanoma skin cancer")
+#define CODE_DCM_NumberOfMalignantMelanomas                                DSRBasicCodedEntry("130483", "DCM", "Number of malignant melanomas")
+#define CODE_DCM_NumberOfMelanomasInSitu                                   DSRBasicCodedEntry("130484", "DCM", "Number of melanomas in situ")
+#define CODE_DCM_FirmSkinLesion                                            DSRBasicCodedEntry("130485", "DCM", "Firm skin lesion")
+#define CODE_DCM_RaisedSkinLesion                                          DSRBasicCodedEntry("130486", "DCM", "Raised skin lesion")
+#define CODE_DCM_NumberOfFirstDegreeRelativesAffectedByMalignantMelanoma   DSRBasicCodedEntry("130487", "DCM", "Number of first-degree relatives affected by malignant melanoma")
+#define CODE_DCM_RegionInSpace                                             DSRBasicCodedEntry("130488", "DCM", "Region in Space")
+#define CODE_DCM_ReferencedRegionOfInterestIdentifier                      DSRBasicCodedEntry("130489", "DCM", "Referenced Region of Interest Identifier")
 
 #endif
index c64cf327c09e026edfba8e28ef8343f584b6a683..935826dff72c419cec0fe6c0707722470e4bc0f8 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file with NCI Thesaurus Code Definitions (Coding Scheme "NCIt")
  *
- *  Generated automatically from DICOM PS 3.16-2019c
- *  File created on 2019-06-19 17:38:36 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 10:55:26 by J. Riesmeier
  *
  */
 
@@ -34,7 +34,7 @@
  *  code definitions  *
  *--------------------*/
 
-// total number of codes: 36
+// total number of codes: 42
 // - retired: 0
 // - no name: 0
 // - not unique: 0
@@ -54,6 +54,8 @@
 #define CODE_NCIt_Technetium99mTrofolastat                                 DSRBasicCodedEntry("C116887", "NCIt", "Technetium^99m Trofolastat")
 #define CODE_NCIt_PSMA11_Ga68                                              DSRBasicCodedEntry("C118961", "NCIt", "PSMA-11 Ga^68^")
 #define CODE_NCIt_Sarcosine_C11                                            DSRBasicCodedEntry("C122684", "NCIt", "Sarcosine C^11^")
+#define CODE_NCIt_SoftTissueSarcoma_excludingRhabdomyosarcoma              DSRBasicCodedEntry("C148457", "NCIt", "Soft tissue sarcoma, excluding rhabdomyosarcoma")
+#define CODE_NCIt_166Holmium                                               DSRBasicCodedEntry("C1943", "NCIt", "^166^Holmium")
 #define CODE_NCIt_MouseMammaryFatPad                                       DSRBasicCodedEntry("C22550", "NCIt", "Mouse mammary fat pad")
 #define CODE_NCIt_Middle                                                   DSRBasicCodedEntry("C25569", "NCIt", "Middle")
 #define CODE_NCIt_Reader                                                   DSRBasicCodedEntry("C28747", "NCIt", "Reader")
 #define CODE_NCIt_AdverseEvent                                             DSRBasicCodedEntry("C41331", "NCIt", "Adverse Event")
 #define CODE_NCIt_TemperatureSensorDeviceComponent                         DSRBasicCodedEntry("C50304", "NCIt", "Temperature sensor device component")
 #define CODE_NCIt_Reviewer                                                 DSRBasicCodedEntry("C54634", "NCIt", "Reviewer")
+#define CODE_NCIt_Ion                                                      DSRBasicCodedEntry("C597", "NCIt", "Ion")
 #define CODE_NCIt_AdLibitum                                                DSRBasicCodedEntry("C64636", "NCIt", "ad libitum")
 #define CODE_NCIt_ActivitySession                                          DSRBasicCodedEntry("C67447", "NCIt", "Activity Session")
 #define CODE_NCIt_UnitConversionFactor                                     DSRBasicCodedEntry("C70774", "NCIt", "Unit Conversion Factor")
 #define CODE_NCIt_MedicalProductExpirationDate                             DSRBasicCodedEntry("C70854", "NCIt", "Medical Product Expiration Date")
+#define CODE_NCIt_CardiotonicAgent                                         DSRBasicCodedEntry("C78322", "NCIt", "Cardiotonic agent")
 #define CODE_NCIt_NonEnhancingLesion                                       DSRBasicCodedEntry("C81175", "NCIt", "Non-Enhancing Lesion")
 #define CODE_NCIt_Erect                                                    DSRBasicCodedEntry("C86043", "NCIt", "erect")
 #define CODE_NCIt_BeddingChange                                            DSRBasicCodedEntry("C90365", "NCIt", "Bedding change")
 #define CODE_NCIt_HousingHumidity                                          DSRBasicCodedEntry("C90395", "NCIt", "Housing humidity")
 #define CODE_NCIt_LightCycle                                               DSRBasicCodedEntry("C90419", "NCIt", "Light cycle")
 #define CODE_NCIt_WaterDelivery                                            DSRBasicCodedEntry("C90486", "NCIt", "Water delivery")
+#define CODE_NCIt_Dosimetrist                                              DSRBasicCodedEntry("C93176", "NCIt", "Dosimetrist")
 #define CODE_NCIt_ReferenceRegion                                          DSRBasicCodedEntry("C94970", "NCIt", "Reference Region")
 #define CODE_NCIt_DCFBC_F18                                                DSRBasicCodedEntry("C96234", "NCIt", "DCFBC F^18^")
 #define CODE_NCIt_Adjudicator                                              DSRBasicCodedEntry("C96561", "NCIt", "Adjudicator")
+#define CODE_NCIt_Fibrate                                                  DSRBasicCodedEntry("C98150", "NCIt", "Fibrate")
 
 #endif
index b6fcb0952e02790abb513ee8febdc6e4e82b2474..a665cf212e09021f52d8afc27ab3a3cccb7d25c1 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Header file with UMLS Code Definitions (Coding Scheme "UMLS")
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 16:52:49 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 10:55:25 by J. Riesmeier
  *
  */
 
@@ -74,6 +74,7 @@
 #define CODE_UMLS_Fluoroetanidazole_F18                                    DSRBasicCodedEntry("C1541539", "UMLS", "Fluoroetanidazole F^18^")
 #define CODE_UMLS_CommercialProduct                                        DSRBasicCodedEntry("C1547887", "UMLS", "Commercial product")
 #define CODE_UMLS_Antihypoglycemic                                         DSRBasicCodedEntry("C1579431", "UMLS", "Antihypoglycemic")
+#define CODE_UMLS_PK11195_11C                                              DSRBasicCodedEntry("C1609883", "UMLS", "PK11195 ^11^C")
 #define CODE_UMLS_Unscheduled                                              DSRBasicCodedEntry("C1699701", "UMLS", "Unscheduled")
 #define CODE_UMLS_Nadir                                                    DSRBasicCodedEntry("C1708760", "UMLS", "Nadir")
 #define CODE_UMLS_MedicalPhysicist                                         DSRBasicCodedEntry("C1708969", "UMLS", "Medical Physicist")
@@ -96,7 +97,6 @@
 #define CODE_UMLS_THK5351_F18                                              DSRBasicCodedEntry("C4279748", "UMLS", "THK5351 F^18^")
 #define CODE_UMLS_MK6240_F18                                               DSRBasicCodedEntry("C4506764", "UMLS", "MK-6240 F^18^")
 #define CODE_UMLS_UCBJ_C11                                                 DSRBasicCodedEntry("C4506788", "UMLS", "UCB-J C^11^")
-#define CODE_UMLS_Flortaucipir_F18                                         DSRBasicCodedEntry("C4547429", "UMLS", "Flortaucipir F^18^")
 #define CODE_UMLS_THK5317_F18                                              DSRBasicCodedEntry("C4550127", "UMLS", "THK5317 F^18^")
 
 #endif
index b61fc6cb051757f6316ab6bb9b069114710492de..83172e7aa1aa642e6f9eeb74c097dc8411d1464b 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2000-2019, OFFIS e.V.
+ *  Copyright (C) 2000-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -263,7 +263,7 @@ class DCMTK_DCMSR_EXPORT DSRDocument
     virtual OFCondition setSpecificCharacterSetType(const E_CharacterSet characterSet);
 
     /** get document preliminary flag.
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      ** @return preliminary flag (might be DSRTypes::PF_invalid if not specified)
      */
     virtual E_PreliminaryFlag getPreliminaryFlag() const;
@@ -271,7 +271,7 @@ class DCMTK_DCMSR_EXPORT DSRDocument
     /** set document preliminary flag.
      *  According to the DICOM standard, the concept of "completeness" is independent of the
      *  concept of "preliminary" or "final".  Therefore, this flag can be specified separately.
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      ** @param  flag  preliminary flag to be set (use DSRTypes::PF_invalid to omit this optional
      *                value)
      ** @return status, EC_Normal if successful, an error code otherwise
@@ -281,19 +281,19 @@ class DCMTK_DCMSR_EXPORT DSRDocument
     /** get document completion flag.
      *  According to the DICOM standard, this flag describes the estimated degree of completeness
      *  of an SR Document.  See DICOM standard for details.
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      ** @return completion flag (might be DSRTypes::CF_invalid if read from dataset)
      */
     virtual E_CompletionFlag getCompletionFlag() const;
 
     /** get document verification flag.
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      ** @return verification flag (might be DSRTypes::VF_invalid if read from dataset)
      */
     virtual E_VerificationFlag getVerificationFlag() const;
 
     /** check whether there are one or more verifying observers.
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      ** @return OFTrue if there is at least one verifying observer, OFFalse otherwise
      */
     virtual OFBool hasVerifyingObservers() const;
@@ -302,7 +302,7 @@ class DCMTK_DCMSR_EXPORT DSRDocument
      *  A document can be verified more than once.  The verification flag should be VERIFIED
      *  if any verifying observer is specified.  The details on the observer can be retrieved
      *  using the getVerifyingObserver() methods.
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      ** @return number of verifying observers (if any), 0 otherwise
      */
     virtual size_t getNumberOfVerifyingObservers() const;
@@ -310,7 +310,7 @@ class DCMTK_DCMSR_EXPORT DSRDocument
     /** get information about a verifying observer.
      *  All reference variables are cleared before the information is retrieved, i.e. if an error
      *  occurs (return value != EC_Normal) non-empty variables do contain valid (empty) data.
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      ** @param  idx           index of the verifying observer to be retrieved (starting with 1).
      *                        Use getNumberOfVerifyingObservers() to get the maximum value.
      *  @param  dateTime      reference to variable where the date and time when this document
@@ -329,7 +329,7 @@ class DCMTK_DCMSR_EXPORT DSRDocument
     /** get information about a verifying observer.
      *  All reference variables are cleared before the information is retrieved, i.e. if an error
      *  occurs (return value != EC_Normal) non-empty variables do contain valid (empty) data.
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      ** @param  idx           index of the verifying observer to be retrieved (starting with 1).
      *                        Use getNumberOfVerifyingObservers() to get the maximum value.
      *  @param  dateTime      reference to variable where the date and time when this document
@@ -357,7 +357,7 @@ class DCMTK_DCMSR_EXPORT DSRDocument
      *  included in this document with or without modification." and "[...] the use of the
      *  Predecessor Document Sequence allows tracing back to the input SR Document, which in this
      *  case is the previous version."
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      ** @return reference to list object
      */
     virtual DSRSOPInstanceReferenceList &getPredecessorDocuments();
@@ -398,7 +398,7 @@ class DCMTK_DCMSR_EXPORT DSRDocument
      *  reference all other evidence considered pertinent for this SR Document that is not listed
      *  in the Current Requested Procedure Evidence Sequence.  This requires that the same SOP
      *  Instance shall not be referenced in both of these Sequences."
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      ** @return reference to list object
      */
     virtual DSRSOPInstanceReferenceList &getPertinentOtherEvidence();
@@ -411,7 +411,7 @@ class DCMTK_DCMSR_EXPORT DSRDocument
      *  Group 7006 (SR Document Purposes of Reference).
      *  Note: An equivalent rendering of the document might be provided as an "Encapsulated PDF"
      *  DICOM object.
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      ** @return reference to list object
      */
     virtual DSRReferencedInstanceList &getReferencedInstances();
@@ -435,7 +435,7 @@ class DCMTK_DCMSR_EXPORT DSRDocument
                                                 const signed long pos = 0) const;
 
     /** get completion flag description.
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      ** @param  value  reference to variable in which the value should be stored
      *  @param  pos    index of the value to get (0..vm-1), -1 for all components
      ** @return status, EC_Normal if successful, an error code otherwise
@@ -740,7 +740,7 @@ class DCMTK_DCMSR_EXPORT DSRDocument
                                                 const OFBool check = OFTrue);
 
     /** set completion flag description.
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      ** @param  value  explanation of the value that is set for completion flag.  If an empty
      *                 string is passed, the description is removed from the dataset (type 3).
      *  @param  check  check 'value' for conformance with VR (LO) and VM (1) if enabled
@@ -1061,7 +1061,7 @@ class DCMTK_DCMSR_EXPORT DSRDocument
      *  reset (OFFalse).  The preliminary flag is not modified by this method.  Also the
      *  various lists of referenced instances remain unchanged, i.e. they have to be
      *  adapted manually if needed.
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      *  @param  clearList  clear list of predecessor documents before adding the current
      *                     document if OFTrue.  Append current document to existing list
      *                     otherwise.
@@ -1074,7 +1074,7 @@ class DCMTK_DCMSR_EXPORT DSRDocument
      *  describes the estimated degree of completeness of an SR Document (see DICOM standard
      *  for details).  The completion flag description is set to an empty string (i.e. absent
      *  in DICOM dataset).
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      ** @return status, EC_Normal if successful, an error code otherwise
      */
     virtual OFCondition completeDocument();
@@ -1084,7 +1084,7 @@ class DCMTK_DCMSR_EXPORT DSRDocument
      *  describes the estimated degree of completeness of an SR Document (see DICOM standard
      *  for details).  The completion flag description can be modified independently from the
      *  flag by means of the method setCompletionFlagDescription() - see above.
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      ** @param  description  explanation of the value set for completion flag.
      *                       (optional, see previous method, VR=LO)
      *  @param  check        check 'description' for conformance with VR and VM if enabled
@@ -1100,7 +1100,7 @@ class DCMTK_DCMSR_EXPORT DSRDocument
      *  Please note that only completed documents (see completion flag) can be verified and that
      *  a new SOP instance UID has to be generated (manually) according to the DICOM standard when
      *  creating a dataset/file from this document.
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      ** @param  observerName  name of the person who has verified this document (required, VR=PN)
      *  @param  organization  name of the organization to which the observer belongs (required, VR=LO)
      *  @param  dateTime      verification date time (optional). If empty/absent the current date and
@@ -1121,7 +1121,7 @@ class DCMTK_DCMSR_EXPORT DSRDocument
      *  Please note that only completed documents (see completion flag) can be verified and that
      *  a new SOP instance UID has to be generated (manually) according to the DICOM standard when
      *  creating a dataset/file from this document.
-     *  @note Not applicable to Key Object Selection Documents.
+     *  @note Not applicable to document types that use the Key Object Document Module.
      ** @param  observerName  name of the person who has verified this document (required, VR=PN)
      *  @param  observerCode  code identifying the verifying observer (optional, see previous method)
      *  @param  organization  name of the organization to which the observer belongs (required, VR=LO)
@@ -1154,9 +1154,9 @@ class DCMTK_DCMSR_EXPORT DSRDocument
      *      document management functions do reset the flag (i.e. set the FinalizedFlag to OFFalse),
      *      other methods (e.g. setXXX) do not change the flag though the state of the document is
      *      not finalized any more after they have been called.
-     *  @note Not applicable to Key Object Selection Documents since there's no completion flag in
-     *        this type of SR document.  Please note that this method has nothing to do with the
-     *        preliminary flag.
+     *  @note Not applicable to document types that use the Key Object Document Module since there
+     *        is no completion flag attribute in this module.  Please note that this method has
+     *        nothing to do with the preliminary flag.
      ** @return status, EC_Normal if successful, an error code otherwise
      */
     virtual OFCondition finalizeDocument();
index 20e7a3c1788e4bfe8c654c559b9a33709da4cd48..0a615fe5edf2a132199323affc11c824c3b72a34 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2000-2018, OFFIS e.V.
+ *  Copyright (C) 2000-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -441,7 +441,7 @@ class DCMTK_DCMSR_EXPORT DSRImageReferenceValue
     /** check the specified SOP class UID for validity.
      *  This method further specializes the checks performed in the base class
      *  DSRCompositeReferenceValue.  All image and segmentation SOP classes that
-     *  are defined in DICOM PS 3.6-2017e are allowed.
+     *  are defined in DICOM PS 3.6-2020c are allowed.
      ** @param  sopClassUID  SOP class UID to be checked
      ** @return status, EC_Normal if value is valid, an error code otherwise
      */
diff --git a/dcmsr/include/dcmtk/dcmsr/dsrrsdcc.h b/dcmsr/include/dcmtk/dcmsr/dsrrsdcc.h
new file mode 100644 (file)
index 0000000..6704449
--- /dev/null
@@ -0,0 +1,94 @@
+/*
+ *
+ *  Copyright (C) 2020, J. Riesmeier, Oldenburg, Germany
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmsr
+ *
+ *  Author: Joerg Riesmeier
+ *
+ *  Purpose:
+ *    classes: DSRRenditionSelectionDocumentConstraintChecker
+ *
+ */
+
+
+#ifndef DSRRSDCC_H
+#define DSRRSDCC_H
+
+#include "dcmtk/config/osconfig.h"   /* make sure OS specific configuration is included first */
+
+#include "dcmtk/dcmsr/dsriodcc.h"
+
+
+/*---------------------*
+ *  class declaration  *
+ *---------------------*/
+
+/** Class for checking the relationship content constraints of the Rendition Selection
+ *  Document IOD.
+ *  According to DICOM PS 3.3: "The document shall be constructed from TID 2010 (Key
+ *  Object Selection) invoked at the root node."
+ */
+class DCMTK_DCMSR_EXPORT DSRRenditionSelectionDocumentConstraintChecker
+  : public DSRIODConstraintChecker
+{
+
+  public:
+
+    /** default constructor
+     */
+    DSRRenditionSelectionDocumentConstraintChecker();
+
+    /** destructor
+     */
+    virtual ~DSRRenditionSelectionDocumentConstraintChecker();
+
+    /** check whether by-reference relationships are allowed for this SR IOD
+     ** @return always returns OFFalse, i.e. by-reference relationships are not allowed
+     */
+    virtual OFBool isByReferenceAllowed() const;
+
+    /** check whether this SR IOD requires template support
+     ** @return always returns OFTrue, i.e. template support is required
+     */
+    virtual OFBool isTemplateSupportRequired() const;
+
+    /** get identifier and mapping resource of the root template (if any)
+     ** @param  templateIdentifier  identifier of the root template (might be empty)
+     *  @param  mappingResource     mapping resource that defines the root template
+     *                              (might be empty)
+     ** @return status, EC_Normal if successful, an error code otherwise
+     */
+    virtual OFCondition getRootTemplateIdentification(OFString &templateIdentifier,
+                                                      OFString &mappingResource) const;
+
+    /** get the associated document type of the SR IOD
+     ** @return document type (DSRTypes::DT_RenditionSelectionDocument)
+     */
+    virtual E_DocumentType getDocumentType() const;
+
+    /** check whether specified content relationship is allowed for this IOD
+     ** @param  sourceValueType   value type of the source content item to be checked
+     *  @param  relationshipType  type of relationship between source and target item
+     *  @param  targetValueType   value type of the target content item to be checked
+     *  @param  byReference       optional flag indicating whether the node/relationship
+     *                            should be added by-value (default) or by-reference
+     ** @return OFTrue if content relationship is allowed, OFFalse otherwise
+     */
+    virtual OFBool checkContentRelationship(const E_ValueType sourceValueType,
+                                            const E_RelationshipType relationshipType,
+                                            const E_ValueType targetValueType,
+                                            const OFBool byReference = OFFalse) const;
+};
+
+
+#endif
index d3915ac92c58737455b257b336a4a37996a15f21..190b3fc56a3b01a7e99fc0e74970bc48ad22649f 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2000-2019, OFFIS e.V.
+ *  Copyright (C) 2000-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -495,7 +495,7 @@ class DCMTK_DCMSR_EXPORT DSRTypes
 
   // --- type definitions ---
 
-    /** SR document types
+    /** SR document types (DICOM IOD)
      */
     enum E_DocumentType
     {
@@ -543,8 +543,10 @@ class DCMTK_DCMSR_EXPORT DSRTypes
         DT_PerformedImagingAgentAdministrationSR,
         /// DICOM IOD: Planned Imaging Agent Administration SR
         DT_PlannedImagingAgentAdministrationSR,
+        /// DICOM IOD: Rendition Selection Document
+        DT_RenditionSelectionDocument,
         /// internal type used to mark the last entry
-        DT_last = DT_PlannedImagingAgentAdministrationSR
+        DT_last = DT_RenditionSelectionDocument
     };
 
     /** SR relationship types
@@ -893,24 +895,52 @@ class DCMTK_DCMSR_EXPORT DSRTypes
     static const char *documentTypeToDocumentTitle(const E_DocumentType documentType,
                                                    OFString &documentTitle);
 
-    /** check whether SR document type requires Enhanced General Equipment Module
+    /** check whether a given SR document type requires the Enhanced General Equipment Module
      ** @param  documentType  SR document type to be checked
-     ** @return OFTrue if Enhanced General Equipment Module is required, OFFalse otherwise
+     ** @return OFTrue if the Enhanced General Equipment Module is required, OFFalse otherwise
      */
     static OFBool requiresEnhancedEquipmentModule(const E_DocumentType documentType);
 
-    /** check whether SR document type requires Timezone Module
+    /** check whether a given SR document type requires the Timezone Module
      ** @param  documentType  SR document type to be checked
-     ** @return OFTrue if Timezone Module is required, OFFalse otherwise
+     ** @return OFTrue if the Timezone Module is required, OFFalse otherwise
      */
     static OFBool requiresTimezoneModule(const E_DocumentType documentType);
 
-    /** check whether SR document type requires Synchronization Module
+    /** check whether a given SR document type requires the Synchronization Module
      ** @param  documentType  SR document type to be checked
-     ** @return OFTrue if Synchronization Module is required, OFFalse otherwise
+     ** @return OFTrue if the Synchronization Module is required, OFFalse otherwise
      */
     static OFBool requiresSynchronizationModule(const E_DocumentType documentType);
 
+    /** check whether a given SR document type uses the SR Document Series Module
+     *  (instead of the Key Object Document Series Module)
+     ** @param  documentType  SR document type to be checked
+     ** @return OFTrue if the SR Document Series Module is used, OFFalse otherwise
+     */
+    static OFBool usesSRDocumentSeriesModule(const E_DocumentType documentType);
+
+    /** check whether a given SR document type uses the Key Object Document Series Module
+     *  (instead of the SR Document Series Module)
+     ** @param  documentType  SR document type to be checked
+     ** @return OFTrue if the Key Object Document Series Module is used, OFFalse otherwise
+     */
+    static OFBool usesKeyObjectDocumentSeriesModule(const E_DocumentType documentType);
+
+    /** check whether a given SR document type uses the SR Document General Module
+     *  (instead of the Key Object Document Module)
+     ** @param  documentType  SR document type to be checked
+     ** @return OFTrue if the SR Document General Module is used, OFFalse otherwise
+     */
+    static OFBool usesSRDocumentGeneralModule(const E_DocumentType documentType);
+
+    /** check whether a given SR document type uses the Key Object Document Module
+     *  (instead of the SR Document General Module)
+     ** @param  documentType  SR document type to be checked
+     ** @return OFTrue if the Key Object Document Module is used, OFFalse otherwise
+     */
+    static OFBool usesKeyObjectDocumentModule(const E_DocumentType documentType);
+
     /** convert relationship type to DICOM defined term
      ** @param  relationshipType  relationship type to be converted
      ** @return defined term if type is valid, empty string otherwise (never NULL)
index c8b457d22c42e9c92dbaca3cf19f709e0a870bc0..a85cf24381efca13c239aec12d6fc391e93c0cae 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2000-2018, OFFIS e.V.
+ *  Copyright (C) 2000-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -216,7 +216,7 @@ class DCMTK_DCMSR_EXPORT DSRWaveformReferenceValue
     /** check the specified SOP class UID for validity.
      *  This method further specializes the checks performed in the base class
      *  DSRCompositeReferenceValue.  All waveform SOP classes that are defined
-     *  in DICOM PS 3.6-2017e are allowed.
+     *  in DICOM PS 3.6-2020c are allowed.
      ** @param  sopClassUID  SOP class UID to be checked
      ** @return status, EC_Normal if value is valid, an error code otherwise
      */
index 5b0880b5a85939896319e31a5af3ae857c06ea1b..f5217ad7821f76dba1319baa66b05954cdf830ed 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2003-2019, OFFIS e.V.
+ *  Copyright (C) 2003-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -125,8 +125,8 @@ class DCMTK_DCMSR_EXPORT DSRXMLDocument
      *  deep search is performed.
      ** @param  cursor    cursor pointing to the node where to start from
      *  @param  name      name of the node (XML element) to be searched for
-     *  @param  required  flag specifying whether the node is required or not.  If the node
-     *                    is required to be present an error message is reported.
+     *  @param  required  flag specifying whether the node is required or not.  If the node is
+     *                    required to be present, an error message is reported if necessary.
      ** @return cursor pointing to the named node if successful, invalid cursor otherwise
      */
     DSRXMLCursor getNamedNode(const DSRXMLCursor &cursor,
@@ -138,8 +138,8 @@ class DCMTK_DCMSR_EXPORT DSRXMLDocument
      *  one, i.e. no deep search is performed.
      ** @param  cursor    cursor pointing to the parent of the node where to start from
      *  @param  name      name of the node (XML element) to be searched for
-     *  @param  required  flag specifying whether the node is required or not.  If the node
-     *                    is required to be present an error message is reported.
+     *  @param  required  flag specifying whether the node is required or not.  If the node is
+     *                    required to be present, an error message is reported if necessary.
      ** @return cursor pointing to the named node if successful, invalid cursor otherwise
      */
     DSRXMLCursor getNamedChildNode(const DSRXMLCursor &cursor,
index b9016c9f6158ae29a97c06e4846385d8b23fc96c..ace0841aaccf32b98f88525f536d84722f714af0 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID100_QuantitativeDiagnosticImagingProcedures
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:14 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:12:49 by J. Riesmeier
  *
  */
 
@@ -18,7 +18,7 @@
 
 // general information on CID 100 (Quantitative Diagnostic Imaging Procedures)
 #define CONTEXT_GROUP_NUMBER  "100"
-#define CONTEXT_GROUP_VERSION "20190121"
+#define CONTEXT_GROUP_VERSION "20190817"
 #define CONTEXT_GROUP_UID     "1.2.840.10008.6.1.998"
 #define CONTEXT_GROUP_TYPE    OFTrue  /* extensible */
 
@@ -162,7 +162,7 @@ CID100_QuantitativeDiagnosticImagingProcedures::CodeList &CID100_QuantitativeDia
         Codes->insert(OFMake_pair(PETUnspecifiedBodyRegion, DSRBasicCodedEntry("44136-0", "LN", "PET unspecified body region")));
         Codes->insert(OFMake_pair(PETWholeBody, DSRBasicCodedEntry("44139-4", "LN", "PET whole body")));
         Codes->insert(OFMake_pair(PETCT_FDGImagingOfWholeBody, DSRBasicCodedEntry("443271005", "SCT", "PET/CT FDG imaging of whole body")));
-        Codes->insert(OFMake_pair(PETCT_METImagingOfWholeBody, DSRBasicCodedEntry("443844003", "SCT", "PET/CT MET imaging of whole body")));
+        Codes->insert(OFMake_pair(PETCT_METImagingOfWholeBody, DSRBasicCodedEntry("764704008", "SCT", "PET/CT MET imaging of whole body")));
         Codes->insert(OFMake_pair(CTPerfusionHeadWithContrastIV, DSRBasicCodedEntry("39142-5", "LN", "CT perfusion head with contrast IV")));
         Codes->insert(OFMake_pair(SPECTBrain, DSRBasicCodedEntry("39632-5", "LN", "SPECT brain")));
         Codes->insert(OFMake_pair(NMHeadPerfusionBrainPET_CT_AV45, DSRBasicCodedEntry("RPID5427", "RADLEX", "NM head perfusion brain PET-CT AV-45")));
index 30ff20cb0ae4eaf812754089c37dc2350487b178..b5b15172f36620dc25ff5568c425f1cc86489ed6 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID10013_CTAcquisitionType
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:39 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:16 by J. Riesmeier
  *
  */
 
index 1839856fc7317c22be5196f60479f259212b7cfe..45940351a2672cd345694c4ac4a09c34193980f2 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID10033_CTReconstructionAlgorithm
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:41 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:18 by J. Riesmeier
  *
  */
 
index 26280725a9ab9f2d2250a9a0945172c5b8bc42c7..3819068cbf000d2b64664b0be187694cc07a4b8b 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID11_RouteOfAdministration
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:09 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:12:44 by J. Riesmeier
  *
  */
 
@@ -18,7 +18,7 @@
 
 // general information on CID 11 (Route of Administration)
 #define CONTEXT_GROUP_NUMBER  "11"
-#define CONTEXT_GROUP_VERSION "20160314"
+#define CONTEXT_GROUP_VERSION "20200117"
 #define CONTEXT_GROUP_UID     "1.2.840.10008.6.1.9"
 #define CONTEXT_GROUP_TYPE    OFTrue  /* extensible */
 
@@ -174,6 +174,7 @@ CID11_RouteOfAdministration::CodeList &CID11_RouteOfAdministration::getCodes()
         Codes->insert(OFMake_pair(NasalRoute, DSRBasicCodedEntry("46713006", "SCT", "Nasal route")));
         Codes->insert(OFMake_pair(IntradermalRoute, DSRBasicCodedEntry("372464004", "SCT", "Intradermal route")));
         Codes->insert(OFMake_pair(IntratumorRoute, DSRBasicCodedEntry("447122006", "SCT", "Intratumor route")));
+        Codes->insert(OFMake_pair(IntracorpusCavernosumRoute, DSRBasicCodedEntry("445769006", "SCT", "Intracorpus cavernosum route")));
     }
     /* should never be NULL */
     return *Codes;
index 5c306897011a06c6e61013ad7518901a31e1b3f6..44a3a71cc08685e9f9f16bb06eea303799bd68a7 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID244_Laterality
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:16 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:12:51 by J. Riesmeier
  *
  */
 
index cada2dd65afcc7a7dc7e29c764ac8fee779321cd..5f4fe3009a057344a2101d0c432ec55b169ca0e9 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID29_AcquisitionModality
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:11 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:12:45 by J. Riesmeier
  *
  */
 
@@ -18,7 +18,7 @@
 
 // general information on CID 29 (Acquisition Modality)
 #define CONTEXT_GROUP_NUMBER  "29"
-#define CONTEXT_GROUP_VERSION "20190327"
+#define CONTEXT_GROUP_VERSION "20201115"
 #define CONTEXT_GROUP_UID     "1.2.840.10008.6.1.19"
 #define CONTEXT_GROUP_TYPE    OFTrue  /* extensible */
 
@@ -150,49 +150,54 @@ CID29_AcquisitionModality::CodeList &CID29_AcquisitionModality::getCodes()
         Codes = new CodeList();
         /* and initialize it by adding the coded entries */
         Codes->insert(OFMake_pair(Autorefraction, DSRBasicCodedEntry("AR", "DCM", "Autorefraction")));
-        Codes->insert(OFMake_pair(UltrasoundBoneDensitometry, DSRBasicCodedEntry("BDUS", "DCM", "Ultrasound Bone Densitometry")));
         Codes->insert(OFMake_pair(BiomagneticImaging, DSRBasicCodedEntry("BI", "DCM", "Biomagnetic Imaging")));
         Codes->insert(OFMake_pair(BoneMineralDensitometry, DSRBasicCodedEntry("BMD", "DCM", "Bone Mineral Densitometry")));
+        Codes->insert(OFMake_pair(CardiacElectrophysiology, DSRBasicCodedEntry("EPS", "DCM", "Cardiac Electrophysiology")));
         Codes->insert(OFMake_pair(ComputedRadiography, DSRBasicCodedEntry("CR", "DCM", "Computed Radiography")));
         Codes->insert(OFMake_pair(ComputedTomography, DSRBasicCodedEntry("CT", "DCM", "Computed Tomography")));
+        Codes->insert(OFMake_pair(Dermoscopy, DSRBasicCodedEntry("DMS", "DCM", "Dermoscopy")));
         Codes->insert(OFMake_pair(Diaphanography, DSRBasicCodedEntry("DG", "DCM", "Diaphanography")));
         Codes->insert(OFMake_pair(DigitalRadiography, DSRBasicCodedEntry("DX", "DCM", "Digital Radiography")));
         Codes->insert(OFMake_pair(Electrocardiography, DSRBasicCodedEntry("ECG", "DCM", "Electrocardiography")));
-        Codes->insert(OFMake_pair(CardiacElectrophysiology, DSRBasicCodedEntry("EPS", "DCM", "Cardiac Electrophysiology")));
+        Codes->insert(OFMake_pair(Electroencephalography, DSRBasicCodedEntry("EEG", "DCM", "Electroencephalography")));
+        Codes->insert(OFMake_pair(Electromyography, DSRBasicCodedEntry("EMG", "DCM", "Electromyography")));
+        Codes->insert(OFMake_pair(Electrooculography, DSRBasicCodedEntry("EOG", "DCM", "Electrooculography")));
         Codes->insert(OFMake_pair(Endoscopy, DSRBasicCodedEntry("ES", "DCM", "Endoscopy")));
+        Codes->insert(OFMake_pair(ExternalCameraPhotography, DSRBasicCodedEntry("XC", "DCM", "External-camera Photography")));
         Codes->insert(OFMake_pair(GeneralMicroscopy, DSRBasicCodedEntry("GM", "DCM", "General Microscopy")));
         Codes->insert(OFMake_pair(HemodynamicWaveform, DSRBasicCodedEntry("HD", "DCM", "Hemodynamic Waveform")));
         Codes->insert(OFMake_pair(IntraOralRadiography, DSRBasicCodedEntry("IO", "DCM", "Intra-oral Radiography")));
         Codes->insert(OFMake_pair(IntravascularOpticalCoherenceTomography, DSRBasicCodedEntry("IVOCT", "DCM", "Intravascular Optical Coherence Tomography")));
         Codes->insert(OFMake_pair(IntravascularUltrasound, DSRBasicCodedEntry("IVUS", "DCM", "Intravascular Ultrasound")));
         Codes->insert(OFMake_pair(Keratometry, DSRBasicCodedEntry("KER", "DCM", "Keratometry")));
-        Codes->insert(OFMake_pair(Lensometry, DSRBasicCodedEntry("LEN", "DCM", "Lensometry")));
         Codes->insert(OFMake_pair(LaserScan, DSRBasicCodedEntry("LS", "DCM", "Laser Scan")));
-        Codes->insert(OFMake_pair(Mammography, DSRBasicCodedEntry("MG", "DCM", "Mammography")));
+        Codes->insert(OFMake_pair(Lensometry, DSRBasicCodedEntry("LEN", "DCM", "Lensometry")));
         Codes->insert(OFMake_pair(MagneticResonance, DSRBasicCodedEntry("MR", "DCM", "Magnetic Resonance")));
+        Codes->insert(OFMake_pair(Mammography, DSRBasicCodedEntry("MG", "DCM", "Mammography")));
         Codes->insert(OFMake_pair(NuclearMedicine, DSRBasicCodedEntry("NM", "DCM", "Nuclear Medicine")));
         Codes->insert(OFMake_pair(OphthalmicAxialMeasurements, DSRBasicCodedEntry("OAM", "DCM", "Ophthalmic Axial Measurements")));
-        Codes->insert(OFMake_pair(OpticalCoherenceTomography, DSRBasicCodedEntry("OCT", "DCM", "Optical Coherence Tomography")));
-        Codes->insert(OFMake_pair(OphthalmicPhotography, DSRBasicCodedEntry("OP", "DCM", "Ophthalmic Photography")));
         Codes->insert(OFMake_pair(OphthalmicMapping, DSRBasicCodedEntry("OPM", "DCM", "Ophthalmic Mapping")));
+        Codes->insert(OFMake_pair(OphthalmicPhotography, DSRBasicCodedEntry("OP", "DCM", "Ophthalmic Photography")));
         Codes->insert(OFMake_pair(OphthalmicTomography, DSRBasicCodedEntry("OPT", "DCM", "Ophthalmic Tomography")));
         Codes->insert(OFMake_pair(OphthalmicTomographyBScanVolumeAnalysis, DSRBasicCodedEntry("OPTBSV", "DCM", "Ophthalmic Tomography B-scan Volume Analysis")));
         Codes->insert(OFMake_pair(OphthalmicTomographyEnFace, DSRBasicCodedEntry("OPTENF", "DCM", "Ophthalmic Tomography En Face")));
         Codes->insert(OFMake_pair(OphthalmicVisualField, DSRBasicCodedEntry("OPV", "DCM", "Ophthalmic Visual Field")));
+        Codes->insert(OFMake_pair(OpticalCoherenceTomography, DSRBasicCodedEntry("OCT", "DCM", "Optical Coherence Tomography")));
         Codes->insert(OFMake_pair(OpticalSurfaceScanner, DSRBasicCodedEntry("OSS", "DCM", "Optical Surface Scanner")));
-        Codes->insert(OFMake_pair(PositronEmissionTomography, DSRBasicCodedEntry("PT", "DCM", "Positron emission tomography")));
         Codes->insert(OFMake_pair(PanoramicXRay, DSRBasicCodedEntry("PX", "DCM", "Panoramic X-Ray")));
-        Codes->insert(OFMake_pair(RespiratoryWaveform, DSRBasicCodedEntry("RESP", "DCM", "Respiratory Waveform")));
+        Codes->insert(OFMake_pair(PositionSensor, DSRBasicCodedEntry("POS", "DCM", "Position Sensor")));
+        Codes->insert(OFMake_pair(PositronEmissionTomography, DSRBasicCodedEntry("PT", "DCM", "Positron emission tomography")));
         Codes->insert(OFMake_pair(Radiofluoroscopy, DSRBasicCodedEntry("RF", "DCM", "Radiofluoroscopy")));
         Codes->insert(OFMake_pair(RadiographicImaging, DSRBasicCodedEntry("RG", "DCM", "Radiographic imaging")));
+        Codes->insert(OFMake_pair(RespiratoryWaveform, DSRBasicCodedEntry("RESP", "DCM", "Respiratory Waveform")));
         Codes->insert(OFMake_pair(RTImage, DSRBasicCodedEntry("RTIMAGE", "DCM", "RT Image")));
         Codes->insert(OFMake_pair(SlideMicroscopy, DSRBasicCodedEntry("SM", "DCM", "Slide Microscopy")));
         Codes->insert(OFMake_pair(SubjectiveRefraction, DSRBasicCodedEntry("SRF", "DCM", "Subjective Refraction")));
         Codes->insert(OFMake_pair(Thermography, DSRBasicCodedEntry("TG", "DCM", "Thermography")));
         Codes->insert(OFMake_pair(Ultrasound, DSRBasicCodedEntry("US", "DCM", "Ultrasound")));
+        Codes->insert(OFMake_pair(UltrasoundBoneDensitometry, DSRBasicCodedEntry("BDUS", "DCM", "Ultrasound Bone Densitometry")));
         Codes->insert(OFMake_pair(VisualAcuity, DSRBasicCodedEntry("VA", "DCM", "Visual Acuity")));
         Codes->insert(OFMake_pair(XRayAngiography, DSRBasicCodedEntry("XA", "DCM", "X-Ray Angiography")));
-        Codes->insert(OFMake_pair(ExternalCameraPhotography, DSRBasicCodedEntry("XC", "DCM", "External-camera Photography")));
     }
     /* should never be NULL */
     return *Codes;
index f6df76744f2a659c5f3ba1f17f27a338530f0f4e..bdaaa6bf444404675d535054f9929f75578fac09 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID4020_PETRadionuclide
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:18 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:12:55 by J. Riesmeier
  *
  */
 
index abb3ca13555e864cd4d75185626227b6020c59a3..f23843480397f980c4d7bfaee71b84a97320619e 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID4021_PETRadiopharmaceutical
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:20 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:12:57 by J. Riesmeier
  *
  */
 
@@ -18,7 +18,7 @@
 
 // general information on CID 4021 (PET Radiopharmaceutical)
 #define CONTEXT_GROUP_NUMBER  "4021"
-#define CONTEXT_GROUP_VERSION "20190124"
+#define CONTEXT_GROUP_VERSION "20201116"
 #define CONTEXT_GROUP_UID     "1.2.840.10008.6.1.305"
 #define CONTEXT_GROUP_TYPE    OFTrue  /* extensible */
 
@@ -149,6 +149,7 @@ CID4021_PETRadiopharmaceutical::CodeList &CID4021_PETRadiopharmaceutical::getCod
         /* create a new code list (should never fail) */
         Codes = new CodeList();
         /* and initialize it by adding the coded entries */
+        Codes->insert(OFMake_pair(_18_FluorineFlortaucipir, DSRBasicCodedEntry("C000591008", "MSH", "^18^Fluorine flortaucipir")));
         Codes->insert(OFMake_pair(_28H1_89Zr, DSRBasicCodedEntry("126752", "DCM", "28H1 ^89^Zr")));
         Codes->insert(OFMake_pair(_2FA_F18, DSRBasicCodedEntry("126713", "DCM", "2FA F^18^")));
         Codes->insert(OFMake_pair(_7D12_89Zr, DSRBasicCodedEntry("126751", "DCM", "7D12 ^89^Zr")));
@@ -185,6 +186,8 @@ CID4021_PETRadiopharmaceutical::CodeList &CID4021_PETRadiopharmaceutical::getCod
         Codes->insert(OFMake_pair(DfFK_89Zr, DSRBasicCodedEntry("126760", "DCM", "Df-FK ^89^Zr")));
         Codes->insert(OFMake_pair(DfFKPEG3_89Zr, DSRBasicCodedEntry("126761", "DCM", "Df-FK-PEG(3) ^89^Zr")));
         Codes->insert(OFMake_pair(DN30_89Zr, DSRBasicCodedEntry("126747", "DCM", "DN30 ^89^Zr")));
+        Codes->insert(OFMake_pair(DPA713_11C, DSRBasicCodedEntry("126765", "DCM", "DPA-713 ^11^C")));
+        Codes->insert(OFMake_pair(DPA714_18F, DSRBasicCodedEntry("126766", "DCM", "DPA-714 ^18^F")));
         Codes->insert(OFMake_pair(E4G10_89Zr, DSRBasicCodedEntry("126519", "DCM", "E4G10 ^89^Zr")));
         Codes->insert(OFMake_pair(Ecromeximab_89Zr, DSRBasicCodedEntry("126732", "DCM", "Ecromeximab ^89^Zr")));
         Codes->insert(OFMake_pair(Edotreotide_Ga68, DSRBasicCodedEntry("C2713594", "UMLS", "Edotreotide Ga^68^")));
@@ -194,7 +197,7 @@ CID4021_PETRadiopharmaceutical::CodeList &CID4021_PETRadiopharmaceutical::getCod
         Codes->insert(OFMake_pair(FLB457_C11, DSRBasicCodedEntry("126706", "DCM", "FLB 457 C^11^")));
         Codes->insert(OFMake_pair(Florbetaben_F18, DSRBasicCodedEntry("712736002", "SCT", "Florbetaben F^18^")));
         Codes->insert(OFMake_pair(Florbetapir_F18, DSRBasicCodedEntry("456995000", "SCT", "Florbetapir F^18^")));
-        Codes->insert(OFMake_pair(Flortaucipir_F18, DSRBasicCodedEntry("C4547429", "UMLS", "Flortaucipir F^18^")));
+        Codes->insert(OFMake_pair(Flortaucipir_F18, DSRBasicCodedEntry("C000591008", "MSH", "Flortaucipir F^18^")));
         Codes->insert(OFMake_pair(Flubatine_F18, DSRBasicCodedEntry("126503", "DCM", "Flubatine F^18^")));
         Codes->insert(OFMake_pair(Fluciclatide_F18, DSRBasicCodedEntry("456999006", "SCT", "Fluciclatide F^18^")));
         Codes->insert(OFMake_pair(Fluciclovine_F18, DSRBasicCodedEntry("457000009", "SCT", "Fluciclovine F^18^")));
@@ -206,7 +209,7 @@ CID4021_PETRadiopharmaceutical::CodeList &CID4021_PETRadiopharmaceutical::getCod
         Codes->insert(OFMake_pair(Fluorodeoxyglucose_F18, DSRBasicCodedEntry("35321007", "SCT", "Fluorodeoxyglucose F^18^")));
         Codes->insert(OFMake_pair(FluoroestradiolFES_F18, DSRBasicCodedEntry("C1831937", "UMLS", "Fluoroestradiol (FES) F^18^")));
         Codes->insert(OFMake_pair(Fluoroetanidazole_F18, DSRBasicCodedEntry("C1541539", "UMLS", "Fluoroetanidazole F^18^")));
-        Codes->insert(OFMake_pair(FluoroLDopa_F18, DSRBasicCodedEntry("129500005", "SCT", "Fluoro-L-dopa F^18^")));
+        Codes->insert(OFMake_pair(FluoroLDopa_F18, DSRBasicCodedEntry("5811000122108", "SCT", "Fluoro-L-dopa F^18^")));
         Codes->insert(OFMake_pair(Fluoromethane_F18, DSRBasicCodedEntry("422763008", "SCT", "Fluoromethane F^18^")));
         Codes->insert(OFMake_pair(Fluoromisonidazole_F18, DSRBasicCodedEntry("422598008", "SCT", "Fluoromisonidazole F^18^")));
         Codes->insert(OFMake_pair(FluoropropylDihydrotetrabenazineDTBZ_F18, DSRBasicCodedEntry("C2934038", "UMLS", "Fluoropropyl-dihydrotetrabenazine (DTBZ) F^18^")));
@@ -216,7 +219,7 @@ CID4021_PETRadiopharmaceutical::CodeList &CID4021_PETRadiopharmaceutical::getCod
         Codes->insert(OFMake_pair(Flutemetamol_F18, DSRBasicCodedEntry("456997008", "SCT", "Flutemetamol F^18^")));
         Codes->insert(OFMake_pair(Fresolimumab_89Zr, DSRBasicCodedEntry("126748", "DCM", "Fresolimumab ^89^Zr")));
         Codes->insert(OFMake_pair(GA201_89Zr, DSRBasicCodedEntry("126731", "DCM", "GA201 ^89^Zr")));
-        Codes->insert(OFMake_pair(Germanium_Ge68, DSRBasicCodedEntry("129516007", "SCT", "Germanium Ge^68^")));
+        Codes->insert(OFMake_pair(Germanium_Ge68, DSRBasicCodedEntry("53315004", "SCT", "Germanium Ge^68^")));
         Codes->insert(OFMake_pair(GlembatumumabVedotin_89Zr, DSRBasicCodedEntry("126724", "DCM", "Glembatumumab vedotin ^89^Zr")));
         Codes->insert(OFMake_pair(Glutamate_N13, DSRBasicCodedEntry("129509006", "SCT", "Glutamate N^13^")));
         Codes->insert(OFMake_pair(Glutamine_C11, DSRBasicCodedEntry("126709", "DCM", "Glutamine C^11^")));
@@ -232,7 +235,7 @@ CID4021_PETRadiopharmaceutical::CodeList &CID4021_PETRadiopharmaceutical::getCod
         Codes->insert(OFMake_pair(Mogamulizumab_89Zr, DSRBasicCodedEntry("126738", "DCM", "Mogamulizumab ^89^Zr")));
         Codes->insert(OFMake_pair(MonoclonalAntibodymAb_64Cu, DSRBasicCodedEntry("126510", "DCM", "Monoclonal Antibody (mAb) ^64^Cu")));
         Codes->insert(OFMake_pair(MonoclonalAntibodymAb_89Zr, DSRBasicCodedEntry("126511", "DCM", "Monoclonal Antibody (mAb) ^89^Zr")));
-        Codes->insert(OFMake_pair(MonoclonalAntibody_I124, DSRBasicCodedEntry("424874008", "SCT", "Monoclonal antibody I^124^")));
+        Codes->insert(OFMake_pair(MonoclonalAntibody_I124, DSRBasicCodedEntry("423249007", "SCT", "Monoclonal antibody I^124^")));
         Codes->insert(OFMake_pair(NanocolloidalAlbumin_89Zr, DSRBasicCodedEntry("126753", "DCM", "Nanocolloidal albumin ^89^Zr")));
         Codes->insert(OFMake_pair(Nifene_F18, DSRBasicCodedEntry("126714", "DCM", "Nifene F^18^")));
         Codes->insert(OFMake_pair(Obinituzimab_89Zr, DSRBasicCodedEntry("126721", "DCM", "Obinituzimab ^89^Zr")));
@@ -244,6 +247,7 @@ CID4021_PETRadiopharmaceutical::CodeList &CID4021_PETRadiopharmaceutical::getCod
         Codes->insert(OFMake_pair(Pegdinetanib_89Zr, DSRBasicCodedEntry("126728", "DCM", "Pegdinetanib ^89^Zr")));
         Codes->insert(OFMake_pair(PinatuzumabVedotin_89Zr, DSRBasicCodedEntry("126725", "DCM", "Pinatuzumab vedotin ^89^Zr")));
         Codes->insert(OFMake_pair(PittsburghCompoundB_C11, DSRBasicCodedEntry("126500", "DCM", "Pittsburgh compound B C^11^")));
+        Codes->insert(OFMake_pair(PK11195_11C, DSRBasicCodedEntry("C1609883", "UMLS", "PK11195 ^11^C")));
         Codes->insert(OFMake_pair(PolatuzumabVedotin_89Zr, DSRBasicCodedEntry("126726", "DCM", "Polatuzumab vedotin ^89^Zr")));
         Codes->insert(OFMake_pair(PSMA1007_F18, DSRBasicCodedEntry("126758", "DCM", "PSMA-1007 F^18^")));
         Codes->insert(OFMake_pair(PSMA11_Ga68, DSRBasicCodedEntry("C118961", "NCIt", "PSMA-11 Ga^68^")));
@@ -264,7 +268,7 @@ CID4021_PETRadiopharmaceutical::CodeList &CID4021_PETRadiopharmaceutical::getCod
         Codes->insert(OFMake_pair(Sarcosine_C11, DSRBasicCodedEntry("C122684", "NCIt", "Sarcosine C^11^")));
         Codes->insert(OFMake_pair(SodiumFluoride_F18, DSRBasicCodedEntry("129501009", "SCT", "Sodium fluoride F^18^")));
         Codes->insert(OFMake_pair(SodiumIodide_I124, DSRBasicCodedEntry("422980002", "SCT", "Sodium iodide I^124^")));
-        Codes->insert(OFMake_pair(Sodium_Na22, DSRBasicCodedEntry("129517003", "SCT", "Sodium Na^22^")));
+        Codes->insert(OFMake_pair(Sodium_Na22, DSRBasicCodedEntry("71633006", "SCT", "Sodium Na^22^")));
         Codes->insert(OFMake_pair(Spiperone_F18, DSRBasicCodedEntry("129499001", "SCT", "Spiperone F^18^")));
         Codes->insert(OFMake_pair(T807_F18, DSRBasicCodedEntry("126502", "DCM", "T807 F^18^")));
         Codes->insert(OFMake_pair(THK5317_F18, DSRBasicCodedEntry("C4550127", "UMLS", "THK5317 F^18^")));
index f54c759c156d641da6e0d4abc599d2ce4b8add1d..f92396b4f14815684358087c2eae1661cad3a205 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID4031_CommonAnatomicRegions
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:22 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:12:59 by J. Riesmeier
  *
  */
 
@@ -18,7 +18,7 @@
 
 // general information on CID 4031 (Common Anatomic Regions)
 #define CONTEXT_GROUP_NUMBER  "4031"
-#define CONTEXT_GROUP_VERSION "20170914"
+#define CONTEXT_GROUP_VERSION "20200704"
 #define CONTEXT_GROUP_UID     "1.2.840.10008.6.1.308"
 #define CONTEXT_GROUP_TYPE    OFTrue  /* extensible */
 
@@ -149,8 +149,8 @@ CID4031_CommonAnatomicRegions::CodeList &CID4031_CommonAnatomicRegions::getCodes
         /* create a new code list (should never fail) */
         Codes = new CodeList();
         /* and initialize it by adding the coded entries */
-        Codes->insert(OFMake_pair(Abdomen, DSRBasicCodedEntry("113345001", "SCT", "Abdomen")));
-        Codes->insert(OFMake_pair(AbdomenAndPelvis, DSRBasicCodedEntry("416949008", "SCT", "Abdomen and Pelvis")));
+        Codes->insert(OFMake_pair(Abdomen, DSRBasicCodedEntry("818981001", "SCT", "Abdomen")));
+        Codes->insert(OFMake_pair(AbdomenAndPelvis, DSRBasicCodedEntry("818982008", "SCT", "Abdomen and Pelvis")));
         Codes->insert(OFMake_pair(AcromioclavicularJoint, DSRBasicCodedEntry("85856004", "SCT", "Acromioclavicular joint")));
         Codes->insert(OFMake_pair(AnkleJoint, DSRBasicCodedEntry("70258002", "SCT", "Ankle joint")));
         Codes->insert(OFMake_pair(Anus, DSRBasicCodedEntry("53505006", "SCT", "Anus")));
@@ -164,12 +164,13 @@ CID4031_CommonAnatomicRegions::CodeList &CID4031_CommonAnatomicRegions::getCodes
         Codes->insert(OFMake_pair(Calcaneus, DSRBasicCodedEntry("80144004", "SCT", "Calcaneus")));
         Codes->insert(OFMake_pair(CervicalSpine, DSRBasicCodedEntry("122494005", "SCT", "Cervical spine")));
         Codes->insert(OFMake_pair(CervicoThoracicSpine, DSRBasicCodedEntry("297171002", "SCT", "Cervico-thoracic spine")));
-        Codes->insert(OFMake_pair(Chest, DSRBasicCodedEntry("51185008", "SCT", "Chest")));
+        Codes->insert(OFMake_pair(Chest, DSRBasicCodedEntry("816094009", "SCT", "Chest")));
         Codes->insert(OFMake_pair(ChestAndAbdomen, DSRBasicCodedEntry("416550000", "SCT", "Chest and Abdomen")));
         Codes->insert(OFMake_pair(ChestAbdomenAndPelvis, DSRBasicCodedEntry("416775004", "SCT", "Chest, Abdomen and Pelvis")));
         Codes->insert(OFMake_pair(Clavicle, DSRBasicCodedEntry("51299004", "SCT", "Clavicle")));
         Codes->insert(OFMake_pair(Coccyx, DSRBasicCodedEntry("64688005", "SCT", "Coccyx")));
         Codes->insert(OFMake_pair(Colon, DSRBasicCodedEntry("71854001", "SCT", "Colon")));
+        Codes->insert(OFMake_pair(CommonBileDuct, DSRBasicCodedEntry("79741001", "SCT", "Common bile duct")));
         Codes->insert(OFMake_pair(Duodenum, DSRBasicCodedEntry("38848004", "SCT", "Duodenum")));
         Codes->insert(OFMake_pair(ElbowJoint, DSRBasicCodedEntry("16953009", "SCT", "Elbow joint")));
         Codes->insert(OFMake_pair(EntireBody, DSRBasicCodedEntry("38266002", "SCT", "Entire body")));
@@ -189,7 +190,8 @@ CID4031_CommonAnatomicRegions::CodeList &CID4031_CommonAnatomicRegions::getCodes
         Codes->insert(OFMake_pair(Head, DSRBasicCodedEntry("69536005", "SCT", "Head")));
         Codes->insert(OFMake_pair(HeadAndNeck, DSRBasicCodedEntry("774007", "SCT", "Head and Neck")));
         Codes->insert(OFMake_pair(Heart, DSRBasicCodedEntry("80891009", "SCT", "Heart")));
-        Codes->insert(OFMake_pair(HipJoint, DSRBasicCodedEntry("29836001", "SCT", "Hip joint")));
+        Codes->insert(OFMake_pair(Hip, DSRBasicCodedEntry("29836001", "SCT", "Hip")));
+        Codes->insert(OFMake_pair(HipJoint, DSRBasicCodedEntry("24136001", "SCT", "Hip Joint")));
         Codes->insert(OFMake_pair(Humerus, DSRBasicCodedEntry("85050009", "SCT", "Humerus")));
         Codes->insert(OFMake_pair(Ileum, DSRBasicCodedEntry("34516001", "SCT", "Ileum")));
         Codes->insert(OFMake_pair(Ilium, DSRBasicCodedEntry("22356005", "SCT", "Ilium")));
@@ -199,6 +201,7 @@ CID4031_CommonAnatomicRegions::CodeList &CID4031_CommonAnatomicRegions::getCodes
         Codes->insert(OFMake_pair(Knee, DSRBasicCodedEntry("72696002", "SCT", "Knee")));
         Codes->insert(OFMake_pair(LargeIntestine, DSRBasicCodedEntry("14742008", "SCT", "Large intestine")));
         Codes->insert(OFMake_pair(Larynx, DSRBasicCodedEntry("4596009", "SCT", "Larynx")));
+        Codes->insert(OFMake_pair(LiverAndBiliaryStructure, DSRBasicCodedEntry("303270005", "SCT", "Liver and biliary structure")));
         Codes->insert(OFMake_pair(LowerLeg, DSRBasicCodedEntry("30021000", "SCT", "Lower leg")));
         Codes->insert(OFMake_pair(LowerLimb, DSRBasicCodedEntry("61685007", "SCT", "Lower limb")));
         Codes->insert(OFMake_pair(LumbarSpine, DSRBasicCodedEntry("122496007", "SCT", "Lumbar spine")));
@@ -216,16 +219,19 @@ CID4031_CommonAnatomicRegions::CodeList &CID4031_CommonAnatomicRegions::getCodes
         Codes->insert(OFMake_pair(NeckChestAbdomenAndPelvis, DSRBasicCodedEntry("416319003", "SCT", "Neck, Chest, Abdomen and Pelvis")));
         Codes->insert(OFMake_pair(OpticCanal, DSRBasicCodedEntry("55024004", "SCT", "Optic canal")));
         Codes->insert(OFMake_pair(OrbitalStructure, DSRBasicCodedEntry("363654007", "SCT", "Orbital structure")));
+        Codes->insert(OFMake_pair(Pancreas, DSRBasicCodedEntry("15776009", "SCT", "Pancreas")));
+        Codes->insert(OFMake_pair(PancreaticDuct, DSRBasicCodedEntry("69930009", "SCT", "Pancreatic duct")));
         Codes->insert(OFMake_pair(PancreaticDuctAndBileDuctSystems, DSRBasicCodedEntry("110621006", "SCT", "Pancreatic duct and bile duct systems")));
         Codes->insert(OFMake_pair(ParanasalSinus, DSRBasicCodedEntry("2095001", "SCT", "Paranasal sinus")));
         Codes->insert(OFMake_pair(ParotidGland, DSRBasicCodedEntry("45289007", "SCT", "Parotid gland")));
         Codes->insert(OFMake_pair(Patella, DSRBasicCodedEntry("64234005", "SCT", "Patella")));
-        Codes->insert(OFMake_pair(Pelvis, DSRBasicCodedEntry("12921003", "SCT", "Pelvis")));
+        Codes->insert(OFMake_pair(Pelvis, DSRBasicCodedEntry("816092008", "SCT", "Pelvis")));
         Codes->insert(OFMake_pair(PelvisAndLowerExtremities, DSRBasicCodedEntry("416631005", "SCT", "Pelvis and lower extremities")));
         Codes->insert(OFMake_pair(Phantom, DSRBasicCodedEntry("113681", "DCM", "Phantom")));
         Codes->insert(OFMake_pair(Prostate, DSRBasicCodedEntry("41216001", "SCT", "Prostate")));
         Codes->insert(OFMake_pair(Rectum, DSRBasicCodedEntry("34402009", "SCT", "Rectum")));
         Codes->insert(OFMake_pair(Rib, DSRBasicCodedEntry("113197003", "SCT", "Rib")));
+        Codes->insert(OFMake_pair(SacroCoccygealSpine, DSRBasicCodedEntry("297174005", "SCT", "Sacro-coccygeal Spine")));
         Codes->insert(OFMake_pair(SacroiliacJoint, DSRBasicCodedEntry("39723000", "SCT", "Sacroiliac joint")));
         Codes->insert(OFMake_pair(Sacrum, DSRBasicCodedEntry("54735007", "SCT", "Sacrum")));
         Codes->insert(OFMake_pair(Scapula, DSRBasicCodedEntry("79601000", "SCT", "Scapula")));
index 6896f7f1f278eaf36221062668ec5294353f07ba..db6f0be7d8b96278c02056070dd6bfb44867d17e 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2018, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID4031e_CommonAnatomicRegions
@@ -30,7 +30,7 @@ struct DefinedTermTypeMapStruct
  *  constant definitions  *
  *------------------------*/
 
-// mapping extracted from DICOM PS 3.16-2018a Table L-1
+// mapping extracted from DICOM PS 3.16-2020c Table L-1
 
 static const DefinedTermTypeMapStruct DefinedTermTypeMap[] =
 {
@@ -50,6 +50,7 @@ static const DefinedTermTypeMapStruct DefinedTermTypeMap[] =
     {"CHESTABDPELVIS",   CID4031_CommonAnatomicRegions::ChestAbdomenAndPelvis},
     {"CLAVICLE",         CID4031_CommonAnatomicRegions::Clavicle},
     {"COCCYX",           CID4031_CommonAnatomicRegions::Coccyx},
+    {"COMMONBILEDUCT",   CID4031_CommonAnatomicRegions::CommonBileDuct},
     {"COLON",            CID4031_CommonAnatomicRegions::Colon},
     {"DUODENUM",         CID4031_CommonAnatomicRegions::Duodenum},
     {"ELBOW",            CID4031_CommonAnatomicRegions::ElbowJoint},
@@ -90,6 +91,8 @@ static const DefinedTermTypeMapStruct DefinedTermTypeMap[] =
     {"NECKCHESTABDPELV", CID4031_CommonAnatomicRegions::NeckChestAbdomenAndPelvis},
     {"OPTICCANAL",       CID4031_CommonAnatomicRegions::OpticCanal},
     {"ORBIT",            CID4031_CommonAnatomicRegions::OrbitalStructure},
+    {"PANCREAS",         CID4031_CommonAnatomicRegions::Pancreas},
+    {"PANCREATICDUCT",   CID4031_CommonAnatomicRegions::PancreaticDuct},
     {"PAROTID",          CID4031_CommonAnatomicRegions::ParotidGland},
     {"PATELLA",          CID4031_CommonAnatomicRegions::Patella},
     {"PELVIS",           CID4031_CommonAnatomicRegions::Pelvis},
index 578937ea98876a40c330f87403aa477d9db0f537..ddd1d1d1fcee9df7e3cdc63f0d35521a3326de52 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID42_NumericValueQualifier
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:12 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:12:47 by J. Riesmeier
  *
  */
 
index 1e69fee1bcb463014d480505ac1f0fe7ddcfc727..a44da5bbe459cf7720c272d9720348979c7b69a7 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID6147_ResponseCriteria
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:24 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:01 by J. Riesmeier
  *
  */
 
index e78cf01ec5f083e5e4f2f738372409306f012ba5..73dba877ace846e4c0ba24056e965fed441800e1 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID7021_MeasurementReportDocumentTitles
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:26 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:03 by J. Riesmeier
  *
  */
 
index 294a9e7ee6fe4a78de40783388296436ad8eabd9..bdd2db76327699ee5335a3761e9c42fde7919f00 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID7181_AbstractMultiDimensionalImageModelComponentUnits
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:28 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:05 by J. Riesmeier
  *
  */
 
index 62348b9165d64bf2d8d6a6987fb6fed7381d45e4..c1417c894e1d0e699ebee9d0bf6d21ffdc9e8cb3 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID7445_DeviceParticipatingRoles
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:30 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:06 by J. Riesmeier
  *
  */
 
index 86daa4f892b2da1bc1bf2fd0005331cfb3549cd4..c725c23934d3c3e0e4c4b99b6dfbc2c6650d619e 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID7452_OrganizationalRoles
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:32 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:08 by J. Riesmeier
  *
  */
 
index 4487988b1dbcb199b6d24931c184408fe4390655..a48f95c31dcbcd10f6af5451f1a9986e80e4bd02 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID7453_PerformingRoles
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:33 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:10 by J. Riesmeier
  *
  */
 
index a7e1c6d1f9237c21a795db188ecdd4927ca3553b..af3124fcaab9cfe0b3f29e5eefc55bcda66a8c7b 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID7464_GeneralRegionOfInterestMeasurementModifiers
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:35 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:12 by J. Riesmeier
  *
  */
 
index e47123a76f60fac05ce1e69d741e77903435d7ad..5ccdd3ba17858393494664b17b3447f6b7aa51ad 100644 (file)
@@ -1,12 +1,12 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  Source file for class CID7469_GenericIntensityAndSizeMeasurements
  *
- *  Generated automatically from DICOM PS 3.16-2019b
- *  File created on 2019-04-26 17:15:37 by J. Riesmeier
+ *  Generated automatically from DICOM PS 3.16-2020e
+ *  File created on 2020-11-25 11:13:14 by J. Riesmeier
  *
  */
 
@@ -303,6 +303,9 @@ CID7469_GenericIntensityAndSizeMeasurements::CodeList &CID7469_GenericIntensityA
         Codes->insert(OFMake_pair(Water, DSRBasicCodedEntry("11713004", "SCT", "Water")));
         Codes->insert(OFMake_pair(WaterFraction, DSRBasicCodedEntry("129103", "DCM", "Water fraction")));
         Codes->insert(OFMake_pair(RelativeLinearStoppingPower, DSRBasicCodedEntry("130086", "DCM", "Relative Linear Stopping Power")));
+        Codes->insert(OFMake_pair(ClassActivation, DSRBasicCodedEntry("130402", "DCM", "Class activation")));
+        Codes->insert(OFMake_pair(GradientWeightedClassActivation, DSRBasicCodedEntry("130403", "DCM", "Gradient-weighted class activation")));
+        Codes->insert(OFMake_pair(Saliency, DSRBasicCodedEntry("130404", "DCM", "Saliency")));
         Codes->insert(OFMake_pair(Length, DSRBasicCodedEntry("410668003", "SCT", "Length")));
         Codes->insert(OFMake_pair(PathLength, DSRBasicCodedEntry("121211", "DCM", "Path length")));
         Codes->insert(OFMake_pair(Distance, DSRBasicCodedEntry("121206", "DCM", "Distance")));
@@ -319,6 +322,7 @@ CID7469_GenericIntensityAndSizeMeasurements::CodeList &CID7469_GenericIntensityA
         Codes->insert(OFMake_pair(Circumference, DSRBasicCodedEntry("74551000", "SCT", "Circumference")));
         Codes->insert(OFMake_pair(DiameterOfCircumscribedCircle, DSRBasicCodedEntry("131192006", "SCT", "Diameter of circumscribed circle")));
         Codes->insert(OFMake_pair(Height, DSRBasicCodedEntry("121207", "DCM", "Height")));
+        Codes->insert(OFMake_pair(LineSegmentLength, DSRBasicCodedEntry("121227", "DCM", "Line segment length")));
         Codes->insert(OFMake_pair(Maximum3DDiameterOfAMesh, DSRBasicCodedEntry("L0JK", "IBSI", "Maximum 3D Diameter of a Mesh")));
         Codes->insert(OFMake_pair(MajorAxisIn3DLength, DSRBasicCodedEntry("TDIC", "IBSI", "Major Axis in 3D Length")));
         Codes->insert(OFMake_pair(MinorAxisIn3DLength, DSRBasicCodedEntry("P9VJ", "IBSI", "Minor Axis in 3D Length")));
index 7315440678ef9857ac464bed78492cd480fa14d6..2139fe3a04d7e284683588b449d496ca2edcc539 100644 (file)
@@ -1,5 +1,5 @@
 # create library from source files
-DCMTK_ADD_LIBRARY(dcmsr dsrcitem dsrcodtn dsrcodvl dsrcomtn dsrcomvl dsrcontn dsrcsidl dsrdattn dsrdncsr dsrdnflt dsrdoc dsrdocst dsrdoctn dsrdoctr dsrdtitn dsrimgfr dsrimgse dsrimgtn dsrimgvl dsritcsr dsrnumtn dsrnumvl dsrpnmtn dsrposcn dsrrefin dsrreftn dsrscogr dsrsc3gr dsrscotn dsrsc3tn dsrscovl dsrsc3vl dsrsoprf dsrstrvl dsrtcodt dsrtcosp dsrtcotn dsrtcoto dsrtcovl dsrtextn dsrtimtn dsrtpltn dsrtree dsrtypes dsruidtn dsrwavch dsrwavtn dsrwavvl dsrxmlc dsrxmld dsriodcc dsrbascc dsrenhcc dsrcomcc dsrkeycc dsrmamcc dsrchecc dsrcolcc dsrprocc dsrxrdcc dsrspecc dsrmaccc dsrimpcc dsrc3dcc dsrrrdcc dsracqcc dsrsaecc dsrprdcc dsrpficc dsrplicc dsrctpl dsrrtpl dsrstpl dsrctxgr)
+DCMTK_ADD_LIBRARY(dcmsr dsrcitem dsrcodtn dsrcodvl dsrcomtn dsrcomvl dsrcontn dsrcsidl dsrdattn dsrdncsr dsrdnflt dsrdoc dsrdocst dsrdoctn dsrdoctr dsrdtitn dsrimgfr dsrimgse dsrimgtn dsrimgvl dsritcsr dsrnumtn dsrnumvl dsrpnmtn dsrposcn dsrrefin dsrreftn dsrscogr dsrsc3gr dsrscotn dsrsc3tn dsrscovl dsrsc3vl dsrsoprf dsrstrvl dsrtcodt dsrtcosp dsrtcotn dsrtcoto dsrtcovl dsrtextn dsrtimtn dsrtpltn dsrtree dsrtypes dsruidtn dsrwavch dsrwavtn dsrwavvl dsrxmlc dsrxmld dsriodcc dsrbascc dsrenhcc dsrcomcc dsrkeycc dsrmamcc dsrchecc dsrcolcc dsrprocc dsrxrdcc dsrspecc dsrmaccc dsrimpcc dsrc3dcc dsrrrdcc dsracqcc dsrsaecc dsrprdcc dsrpficc dsrplicc dsrrsdcc dsrctpl dsrrtpl dsrstpl dsrctxgr)
 
 DCMTK_TARGET_LINK_MODULES(dcmsr ofstd oflog dcmdata dcmimgle dcmimage)
 DCMTK_TARGET_LINK_LIBRARIES(dcmsr ${LIBXML_LIBS})
index bc1c80a9eb844feab5bab4415b7338100236940c..0f30cf9815ee303f26e362905b27d674b356d6c6 100644 (file)
@@ -34,7 +34,7 @@ objs = dsrdoc.o dsrposcn.o dsrdncsr.o dsritcsr.o dsrdnflt.o dsrtree.o \
        dsriodcc.o dsrbascc.o dsrenhcc.o dsrcomcc.o dsrkeycc.o dsrmamcc.o \
        dsrchecc.o dsrcolcc.o dsrprocc.o dsrxrdcc.o dsrspecc.o dsrmaccc.o \
        dsrimpcc.o dsrc3dcc.o dsrrrdcc.o dsracqcc.o dsrsaecc.o dsrprdcc.o \
-       dsrpficc.o dsrplicc.o
+       dsrpficc.o dsrplicc.o dsrrsdcc.o
 library = libdcmsr.$(LIBEXT)
 
 
index f3604e7122a89a38a84f655817e65845a67fc9d4..c46fc202037c83166354114aade2fa2030c99556 100644 (file)
@@ -768,12 +768,20 @@ OFCondition DSRCodedEntryValue::checkCode(const OFString &codeValue,
 {
     OFCondition result = EC_Normal;
     /* first, make sure that the mandatory values are non-empty and the type is valid */
-    if (codeValue.empty() || (codingSchemeDesignator.empty() && (codeValueType != DSRTypes::CVT_URN)) || codeMeaning.empty())
-        result = SR_EC_InvalidValue;
+    if (codeValueType == DSRTypes::CVT_URN)
+    {
+        /* CP-1913: Coding Scheme Version shall not be present if Coding Scheme Designator is absent */
+        if (codeValue.empty() || (codingSchemeDesignator.empty() && !codingSchemeVersion.empty()) || codeMeaning.empty())
+            result = SR_EC_InvalidValue;
+    }
     else if (codeValueType == DSRTypes::CVT_auto)
     {
         DCMSR_DEBUG("INTERNAL ERROR: DSRCodedEntryValue::checkCode() called with DSRTypes::CVT_auto");
         result = EC_IllegalCall;
+    } else {
+        /* short or long code value */
+        if (codeValue.empty() || codingSchemeDesignator.empty() || codeMeaning.empty())
+            result = SR_EC_InvalidValue;
     }
     /* then, check whether the passed values are valid with regards to VR and VM.
      * tbd: unfortunately, we do not know the character set, so "UNKNOWN" is used. */
index 6ba96ed5e470724f88ab323a8e7894aaa55ac9f9..6a70c63a1c8ffeb5b94a2db2c0f918fe3d2df32a 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2000-2019, OFFIS e.V.
+ *  Copyright (C) 2000-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -209,6 +209,8 @@ OFCondition DSRDocument::print(STD_NAMESPACE ostream &stream,
         OFString tmpString, string2;
         /* update only some DICOM attributes */
         updateAttributes(OFFalse /*updateAll*/);
+        /* check whether general SR modules are used */
+        const OFBool usesGeneralSRModules = usesSRDocumentGeneralModule(getDocumentType());
 
         // --- print some general document information ---
 
@@ -300,8 +302,8 @@ OFCondition DSRDocument::print(STD_NAMESPACE ostream &stream,
                     stream << " (" << deviceStr << ")";
                 DCMSR_PRINT_HEADER_FIELD_END
             }
-            /* Key Object Selection Documents do not contain the SR Document General Module */
-            if (getDocumentType() != DT_KeyObjectSelectionDocument)
+            /* not all SR IODs contain the SR Document General Module */
+            if (usesGeneralSRModules)
             {
                 /* preliminary flag */
                 if (!PreliminaryFlag.isEmpty())
@@ -342,7 +344,7 @@ OFCondition DSRDocument::print(STD_NAMESPACE ostream &stream,
                 stream << ReferencedInstances.getNumberOfItems();
                 DCMSR_PRINT_HEADER_FIELD_END
             }
-            if (getDocumentType() != DT_KeyObjectSelectionDocument)
+            if (usesGeneralSRModules)
             {
                 /* verification flag */
                 DCMSR_PRINT_HEADER_FIELD_START("Verification Flag  ", " : ")
@@ -421,7 +423,7 @@ OFCondition DSRDocument::checkDatasetForReading(DcmItem &dataset,
     /* check modality */
     if (result.good())
     {
-        if (documentType == DT_KeyObjectSelectionDocument)
+        if (usesKeyObjectDocumentSeriesModule(documentType))
             result = getAndCheckElementFromDataset(dataset, modality, "1", "1", "KeyObjectDocumentSeriesModule");
         else
             result = getAndCheckElementFromDataset(dataset, modality, "1", "1", "SRDocumentSeriesModule");
@@ -508,7 +510,7 @@ OFCondition DSRDocument::read(DcmItem &dataset,
 
         // --- SR Document Series Module / Key Object Document Series Module ---
         getElementFromDataset(dataset, Modality);   /* already checked */
-        if (documentType == DT_KeyObjectSelectionDocument)
+        if (usesKeyObjectDocumentSeriesModule(documentType))
         {
             getAndCheckElementFromDataset(dataset, SeriesInstanceUID, "1", "1", "KeyObjectDocumentSeriesModule");
             getAndCheckElementFromDataset(dataset, SeriesNumber, "1", "1", "KeyObjectDocumentSeriesModule");
@@ -535,7 +537,7 @@ OFCondition DSRDocument::read(DcmItem &dataset,
         removeAttributeFromSequence(ReferencedPerformedProcedureStep, DCM_DigitalSignaturesSequence);
 
         // --- SR Document General Module / Key Object Document Module ---
-        if (documentType == DT_KeyObjectSelectionDocument)
+        if (usesKeyObjectDocumentModule(documentType))
         {
             getAndCheckElementFromDataset(dataset, InstanceNumber, "1", "1", "KeyObjectDocumentModule");
             getAndCheckElementFromDataset(dataset, ContentDate, "1", "1", "KeyObjectDocumentModule");
@@ -566,8 +568,8 @@ OFCondition DSRDocument::read(DcmItem &dataset,
 
         /* update internal enumerated values and perform additional checks */
 
-        /* Key Object Selection Documents do not contain the SR Document General Module */
-        if (documentType != DT_KeyObjectSelectionDocument)
+        /* not all SR IODs contain the SR Document General Module */
+        if (usesSRDocumentGeneralModule(documentType))
         {
             /* get and check PreliminaryFlag (if present) */
             if (!PreliminaryFlag.isEmpty())
@@ -580,7 +582,7 @@ OFCondition DSRDocument::read(DcmItem &dataset,
             CompletionFlagEnum = enumeratedValueToCompletionFlag(getStringValueFromElement(CompletionFlag, tmpString));
             if (CompletionFlagEnum == CF_invalid)
                 printUnknownValueWarningMessage("CompletionFlag", tmpString.c_str());
-            else if ((CompletionFlagEnum == CF_Partial) && (documentType == DT_XRayRadiationDoseSR))
+            else if ((documentType == DT_XRayRadiationDoseSR) && (CompletionFlagEnum != CF_Complete))
                 DCMSR_WARN("Invalid value for Completion Flag, should be 'COMPLETE' for X-Ray Radiation Dose SR");
             /* get and check VerificationFlag / VerifyingObserverSequence */
             VerificationFlagEnum = enumeratedValueToVerificationFlag(getStringValueFromElement(VerificationFlag, tmpString));
@@ -645,7 +647,7 @@ OFCondition DSRDocument::write(DcmItem &dataset,
         updateAttributes();
 
         /* checking particular values */
-        if ((CompletionFlagEnum == CF_Partial) && (getDocumentType() == DT_XRayRadiationDoseSR))
+        if ((getDocumentType() == DT_XRayRadiationDoseSR) && (CompletionFlagEnum != CF_Complete))
             DCMSR_WARN("Invalid value for Completion Flag, should be 'COMPLETE' for X-Ray Radiation Dose SR");
 
         /* write general document attributes */
@@ -710,7 +712,7 @@ OFCondition DSRDocument::write(DcmItem &dataset,
         }
 
         // --- SR Document Series Module / Key Object Document Series Module ---
-        if (getDocumentType() == DT_KeyObjectSelectionDocument)
+        if (usesKeyObjectDocumentSeriesModule(getDocumentType()))
         {
             addElementToDataset(result, dataset, new DcmCodeString(Modality), "1", "1", "KeyObjectDocumentSeriesModule");
             addElementToDataset(result, dataset, new DcmUniqueIdentifier(SeriesInstanceUID), "1", "1", "KeyObjectDocumentSeriesModule");
@@ -736,7 +738,7 @@ OFCondition DSRDocument::write(DcmItem &dataset,
         }
 
         // --- SR Document General Module / Key Object Document Module ---
-        if (getDocumentType() == DT_KeyObjectSelectionDocument)
+        if (usesKeyObjectDocumentModule(getDocumentType()))
         {
             addElementToDataset(result, dataset, new DcmIntegerString(InstanceNumber), "1", "1", "KeyObjectDocumentModule");
             addElementToDataset(result, dataset, new DcmDate(ContentDate), "1", "1", "KeyObjectDocumentModule");
@@ -911,7 +913,7 @@ OFCondition DSRDocument::readXMLDocumentHeader(DSRXMLDocument &doc,
                     result = CurrentRequestedProcedureEvidence.readXML(doc, cursor.getChild(), flags);
                 else if (typeString == "Pertinent Other")
                 {
-                    if (getDocumentType() != DT_KeyObjectSelectionDocument)
+                    if (usesSRDocumentGeneralModule(getDocumentType()))
                         result = PertinentOtherEvidence.readXML(doc, cursor.getChild(), flags);
                     else
                         doc.printUnexpectedNodeWarning(cursor);
@@ -1131,21 +1133,22 @@ OFCondition DSRDocument::readXMLDocumentData(const DSRXMLDocument &doc,
     if (cursor.valid())
     {
         OFString tmpString;
-        const E_DocumentType documentType = getDocumentType();
+        /* check whether general SR modules are used */
+        const OFBool usesGeneralSRModules = usesSRDocumentGeneralModule(getDocumentType());
         result = EC_Normal;
         /* iterate over all nodes */
         while (cursor.valid() && result.good())
         {
             /* check for known element tags
-               (Key Object Selection Documents do not contain the SR Document General Module) */
-            if ((documentType != DT_KeyObjectSelectionDocument) && doc.matchNode(cursor, "preliminary"))
+               (not all SR IODs contain the SR Document General Module) */
+            if (usesGeneralSRModules && doc.matchNode(cursor, "preliminary"))
             {
                 /* Preliminary Flag */
                 PreliminaryFlagEnum = enumeratedValueToPreliminaryFlag(doc.getStringFromAttribute(cursor, tmpString, "flag"));
                 if (PreliminaryFlagEnum == PF_invalid)
                     printUnknownValueWarningMessage("PreliminaryFlag", tmpString.c_str());
             }
-            else if ((documentType != DT_KeyObjectSelectionDocument) && doc.matchNode(cursor, "completion"))
+            else if (usesGeneralSRModules && doc.matchNode(cursor, "completion"))
             {
                 /* Completion Flag */
                 CompletionFlagEnum = enumeratedValueToCompletionFlag(doc.getStringFromAttribute(cursor, tmpString, "flag"));
@@ -1158,7 +1161,7 @@ OFCondition DSRDocument::readXMLDocumentData(const DSRXMLDocument &doc,
                 } else
                     printUnknownValueWarningMessage("CompletionFlag", tmpString.c_str());
             }
-            else if ((documentType != DT_KeyObjectSelectionDocument) && doc.matchNode(cursor, "verification"))
+            else if (usesGeneralSRModules && doc.matchNode(cursor, "verification"))
             {
                 /* Verification Flag */
                 VerificationFlagEnum = enumeratedValueToVerificationFlag(doc.getStringFromAttribute(cursor, tmpString, "flag"));
@@ -1172,7 +1175,7 @@ OFCondition DSRDocument::readXMLDocumentData(const DSRXMLDocument &doc,
                 } else
                     printUnknownValueWarningMessage("VerificationFlag", tmpString.c_str());
             }
-            else if ((documentType != DT_KeyObjectSelectionDocument) && doc.matchNode(cursor, "predecessor"))
+            else if (usesGeneralSRModules && doc.matchNode(cursor, "predecessor"))
             {
                 /* Predecessor Documents Sequence (optional) */
                 result = PredecessorDocuments.readXML(doc, cursor.getChild(), flags);
@@ -1280,6 +1283,8 @@ OFCondition DSRDocument::writeXML(STD_NAMESPACE ostream &stream,
         OFString tmpString;
         /* update all DICOM attributes */
         updateAttributes();
+        /* check whether general SR modules are used */
+        const OFBool usesGeneralSRModules = usesSRDocumentGeneralModule(getDocumentType());
 
         // --- XML document structure (start) ---
 
@@ -1414,7 +1419,7 @@ OFCondition DSRDocument::writeXML(STD_NAMESPACE ostream &stream,
             CurrentRequestedProcedureEvidence.writeXML(stream, flags);
             stream << "</evidence>" << OFendl;
         }
-        if (getDocumentType() != DT_KeyObjectSelectionDocument)
+        if (usesGeneralSRModules)
         {
             if ((flags & XF_writeEmptyTags) || !PertinentOtherEvidence.isEmpty())
             {
@@ -1431,7 +1436,7 @@ OFCondition DSRDocument::writeXML(STD_NAMESPACE ostream &stream,
         }
 
         stream << "<document>" << OFendl;
-        if (getDocumentType() != DT_KeyObjectSelectionDocument)
+        if (usesGeneralSRModules)
         {
             if (!PreliminaryFlag.isEmpty())
                 stream << "<preliminary flag=\"" << getStringValueFromElement(PreliminaryFlag, tmpString) << "\"/>" << OFendl;
@@ -1648,6 +1653,8 @@ OFCondition DSRDocument::renderHTML(STD_NAMESPACE ostream &stream,
         OFString htmlString;
         /* update only some DICOM attributes */
         updateAttributes(OFFalse /*updateAll*/);
+        /* check whether general SR modules are used */
+        const OFBool usesGeneralSRModules = usesSRDocumentGeneralModule(getDocumentType());
 
         // --- HTML/XHTML document structure (start) ---
 
@@ -1821,7 +1828,7 @@ OFCondition DSRDocument::renderHTML(STD_NAMESPACE ostream &stream,
                 stream << "</td>" << OFendl;
                 stream << "</tr>" << OFendl;
             }
-            if (getDocumentType() != DT_KeyObjectSelectionDocument)
+            if (usesGeneralSRModules)
             {
                 /* preliminary flag */
                 if (!PreliminaryFlag.isEmpty())
@@ -1870,7 +1877,7 @@ OFCondition DSRDocument::renderHTML(STD_NAMESPACE ostream &stream,
                 renderHTMLReferenceList(stream, ReferencedInstances, flags);
                 stream << "</tr>" << OFendl;
             }
-            if (getDocumentType() != DT_KeyObjectSelectionDocument)
+            if (usesGeneralSRModules)
             {
                 /* verification flag */
                 stream << "<tr>" << OFendl;
@@ -2063,8 +2070,8 @@ DSRTypes::E_PreliminaryFlag DSRDocument::getPreliminaryFlag() const
 OFCondition DSRDocument::setPreliminaryFlag(const E_PreliminaryFlag flag)
 {
     OFCondition result = EC_IllegalCall;
-    /* not applicable to Key Object Selection Documents */
-    if (getDocumentType() != DT_KeyObjectSelectionDocument)
+    /* not all SR IODs contain the SR Document General Module */
+    if (usesSRDocumentGeneralModule(getDocumentType()))
     {
         PreliminaryFlagEnum = flag;
         result = EC_Normal;
@@ -2476,8 +2483,8 @@ OFCondition DSRDocument::setCompletionFlagDescription(const OFString &value,
                                                       const OFBool check)
 {
     OFCondition result = EC_IllegalCall;
-    /* not applicable to Key Object Selection Documents */
-    if (getDocumentType() != DT_KeyObjectSelectionDocument)
+    /* not all SR IODs contain the SR Document General Module */
+    if (usesSRDocumentGeneralModule(getDocumentType()))
     {
         if (check)
             result = DcmLongString::checkStringValue(value, "1", getSpecificCharacterSet());
@@ -2855,8 +2862,8 @@ OFCondition DSRDocument::changeDocumentType(const E_DocumentType documentType)
 OFCondition DSRDocument::createRevisedVersion(const OFBool clearList)
 {
     OFCondition result = EC_IllegalCall;
-    /* not applicable to Key Object Selection Documents */
-    if (getDocumentType() != DT_KeyObjectSelectionDocument)
+    /* not all SR IODs contain the SR Document General Module */
+    if (usesSRDocumentGeneralModule(getDocumentType()))
     {
         /* check whether document is already completed */
         if (CompletionFlagEnum == CF_Complete)
@@ -2902,8 +2909,8 @@ OFCondition DSRDocument::completeDocument(const OFString &description,
                                           const OFBool check)
 {
     OFCondition result = EC_IllegalCall;
-    /* not applicable to Key Object Selection Documents */
-    if (getDocumentType() != DT_KeyObjectSelectionDocument)
+    /* not all SR IODs contain the SR Document General Module */
+    if (usesSRDocumentGeneralModule(getDocumentType()))
     {
         /* if document is not already completed */
         if (CompletionFlagEnum != CF_Complete)
@@ -2940,8 +2947,8 @@ OFCondition DSRDocument::verifyDocument(const OFString &observerName,
                                         const OFBool check)
 {
     OFCondition result = EC_IllegalCall;
-    /* not applicable to Key Object Selection Documents */
-    if (getDocumentType() != DT_KeyObjectSelectionDocument)
+    /* not all SR IODs contain the SR Document General Module */
+    if (usesSRDocumentGeneralModule(getDocumentType()))
     {
         /* verify completed documents only */
         if (CompletionFlagEnum == CF_Complete)
@@ -3087,18 +3094,9 @@ void DSRDocument::updateAttributes(const OFBool updateAll,
         if (ContentTime.isEmpty())
             ContentTime.putString(getStringValueFromElement(InstanceCreationTime));
     }
-    if (documentType == DT_KeyObjectSelectionDocument)
+    /* not all SR IODs contain the SR Document General Module */
+    if (usesSRDocumentGeneralModule(documentType))
     {
-        /* these flags are not used for Key Object Selection Documents */
-        PreliminaryFlagEnum = PF_invalid;
-        CompletionFlagEnum = CF_invalid;
-        VerificationFlagEnum = VF_invalid;
-        PreliminaryFlag.clear();
-        CompletionFlag.clear();
-        CompletionFlagDescription.clear();
-        VerificationFlag.clear();
-        VerifyingObserver.clear();
-    } else {
         /* set preliminary flag */
         PreliminaryFlag.putString(preliminaryFlagToEnumeratedValue(PreliminaryFlagEnum));
         /* check and adjust completion flag if required */
@@ -3109,5 +3107,15 @@ void DSRDocument::updateAttributes(const OFBool updateAll,
         if (VerificationFlagEnum == VF_invalid)
             VerificationFlagEnum = VF_Unverified;
         VerificationFlag.putString(verificationFlagToEnumeratedValue(VerificationFlagEnum));
+    } else {
+        /* if not, reset the various flags and clear related information */
+        PreliminaryFlagEnum = PF_invalid;
+        CompletionFlagEnum = CF_invalid;
+        VerificationFlagEnum = VF_invalid;
+        PreliminaryFlag.clear();
+        CompletionFlag.clear();
+        CompletionFlagDescription.clear();
+        VerificationFlag.clear();
+        VerifyingObserver.clear();
     }
 }
index a15a7fa189442cc827aedbbf36d66a4acee24f0b..8e50acf5e062f2f33aca3abec9ee32f02ea887c7 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2000-2018, OFFIS e.V.
+ *  Copyright (C) 2000-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -688,7 +688,7 @@ OFBool DSRImageReferenceValue::appliesToSegment(const Uint16 segmentNumber) cons
 
 OFBool DSRImageReferenceValue::isSegmentationObject(const OFString &sopClassUID) const
 {
-    /* check for all segmentation SOP classes (according to DICOM PS 3.6-2017e) */
+    /* check for all segmentation SOP classes (according to DICOM PS 3.6-2020c) */
     return (sopClassUID == UID_SegmentationStorage) || (sopClassUID == UID_SurfaceSegmentationStorage);
 }
 
index b8c142a66215044cfe5b6027a51bbdf93c1f74fa..468593918500cdb12047805c0c42acd82e98099d 100644 (file)
@@ -77,27 +77,27 @@ OFBool DSRPerformedImagingAgentAdministrationSRConstraintChecker::checkContentRe
         /* row 1 of the table */
         if ((relationshipType == RT_contains) && (sourceValueType == VT_Container))
         {
-            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code)     || (targetValueType == VT_Num)       ||
-                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date)     || (targetValueType == VT_Time)      ||
-                     (targetValueType == VT_UIDRef)   || (targetValueType == VT_PName)    || (targetValueType == VT_Composite) ||
-                     (targetValueType == VT_Image)    || (targetValueType == VT_Waveform) || (targetValueType == VT_Container);
+            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code)      || (targetValueType == VT_Num)    ||
+                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date)      || (targetValueType == VT_UIDRef) ||
+                     (targetValueType == VT_PName)    || (targetValueType == VT_Composite) || (targetValueType == VT_Image)  ||
+                     (targetValueType == VT_Waveform) || (targetValueType == VT_Container);
         }
         /* row 2 of the table */
         else if ((relationshipType == RT_hasObsContext) &&
             ((sourceValueType == VT_Text) || (sourceValueType == VT_Code) || (sourceValueType == VT_Num) || (sourceValueType == VT_Container)))
         {
-            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code)  || (targetValueType == VT_Num)  ||
-                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date)  || (targetValueType == VT_Time) ||
-                     (targetValueType == VT_UIDRef)   || (targetValueType == VT_PName) || (targetValueType == VT_Composite);
+            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code) || (targetValueType == VT_Num)    ||
+                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date) || (targetValueType == VT_UIDRef) ||
+                     (targetValueType == VT_PName)    || (targetValueType == VT_Composite);
         }
         /* row 3 of the table */
         else if ((relationshipType == RT_hasAcqContext) &&
             ((sourceValueType == VT_Container) || (sourceValueType == VT_Image) || (sourceValueType == VT_Waveform) ||
              (sourceValueType == VT_Composite) || (sourceValueType == VT_Num)))
         {
-            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code)  || (targetValueType == VT_Num)  ||
-                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date)  || (targetValueType == VT_Time) ||
-                     (targetValueType == VT_UIDRef)   || (targetValueType == VT_PName) || (targetValueType == VT_Container);
+            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code) || (targetValueType == VT_Num)    ||
+                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date) || (targetValueType == VT_UIDRef) ||
+                     (targetValueType == VT_PName)    || (targetValueType == VT_Container);
         }
         /* row 4 of the table */
         else if (relationshipType == RT_hasConceptMod)
@@ -108,26 +108,25 @@ OFBool DSRPerformedImagingAgentAdministrationSRConstraintChecker::checkContentRe
         else if ((relationshipType == RT_hasProperties) &&
             ((sourceValueType == VT_Text) || (sourceValueType == VT_Code) || (sourceValueType == VT_Num)))
         {
-            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code)      || (targetValueType == VT_Num)   ||
-                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date)      || (targetValueType == VT_Time)  ||
-                     (targetValueType == VT_UIDRef)   || (targetValueType == VT_PName)     || (targetValueType == VT_Image) ||
-                     (targetValueType == VT_Waveform) || (targetValueType == VT_Composite) || (targetValueType == VT_Container);
+            result = (targetValueType == VT_Text)      || (targetValueType == VT_Code)  || (targetValueType == VT_Num)     ||
+                     (targetValueType == VT_DateTime)  || (targetValueType == VT_Date)  || (targetValueType == VT_UIDRef)  ||
+                     (targetValueType == VT_PName)     || (targetValueType == VT_Image) ||(targetValueType == VT_Waveform) ||
+                     (targetValueType == VT_Composite) || (targetValueType == VT_Container);
         }
         /* row 6 of the table */
         else if ((relationshipType == RT_hasProperties) && (sourceValueType == VT_PName))
         {
-            result = (targetValueType == VT_Text)  || (targetValueType == VT_Code) || (targetValueType == VT_DateTime) ||
-                     (targetValueType == VT_Date)  || (targetValueType == VT_Time) || (targetValueType == VT_UIDRef)   ||
-                     (targetValueType == VT_PName);
+            result = (targetValueType == VT_Text) || (targetValueType == VT_Code)   || (targetValueType == VT_DateTime) ||
+                     (targetValueType == VT_Date) || (targetValueType == VT_UIDRef) ||(targetValueType == VT_PName);
         }
         /* row 7 of the table */
         else if ((relationshipType == RT_inferredFrom) &&
             ((sourceValueType == VT_Text) || (sourceValueType == VT_Code) || (sourceValueType == VT_Num)))
         {
-            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code)      || (targetValueType == VT_Num)   ||
-                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date)      || (targetValueType == VT_Time)  ||
-                     (targetValueType == VT_UIDRef)   || (targetValueType == VT_PName)     || (targetValueType == VT_Image) ||
-                     (targetValueType == VT_Waveform) || (targetValueType == VT_Composite) || (targetValueType == VT_Container);
+            result = (targetValueType == VT_Text)      || (targetValueType == VT_Code)  || (targetValueType == VT_Num)      ||
+                     (targetValueType == VT_DateTime)  || (targetValueType == VT_Date)  || (targetValueType == VT_UIDRef)   ||
+                     (targetValueType == VT_PName)     || (targetValueType == VT_Image) || (targetValueType == VT_Waveform) ||
+                     (targetValueType == VT_Composite) || (targetValueType == VT_Container);
         }
     }
     return result;
index e9c4218f83ffc593c8f92b3d601323e9968eaa9d..ad1de2fc80484972283512e84faf1616e08b5246 100644 (file)
@@ -77,25 +77,25 @@ OFBool DSRPlannedImagingAgentAdministrationSRConstraintChecker::checkContentRela
         /* row 1 of the table */
         if ((relationshipType == RT_contains) && (sourceValueType == VT_Container))
         {
-            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code)  || (targetValueType == VT_Num)  ||
-                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date)  || (targetValueType == VT_Time) ||
-                     (targetValueType == VT_UIDRef)   || (targetValueType == VT_PName) || (targetValueType == VT_Container);
+            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code) || (targetValueType == VT_Num)    ||
+                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date) || (targetValueType == VT_UIDRef) ||
+                     (targetValueType == VT_PName)    || (targetValueType == VT_Container);
         }
         /* row 2 of the table */
         else if ((relationshipType == RT_hasObsContext) &&
             ((sourceValueType == VT_Text) || (sourceValueType == VT_Code) || (sourceValueType == VT_Num) || (sourceValueType == VT_Container)))
         {
-            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code)  || (targetValueType == VT_Num)  ||
-                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date)  || (targetValueType == VT_Time) ||
-                     (targetValueType == VT_UIDRef)   || (targetValueType == VT_PName);
+            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code) || (targetValueType == VT_Num)    ||
+                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date) || (targetValueType == VT_UIDRef) ||
+                     (targetValueType == VT_PName);
         }
         /* row 3 of the table */
         else if ((relationshipType == RT_hasAcqContext) &&
             ((sourceValueType == VT_Container) || (sourceValueType == VT_Num)))
         {
-            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code)  || (targetValueType == VT_Num)  ||
-                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date)  || (targetValueType == VT_Time) ||
-                     (targetValueType == VT_UIDRef)   || (targetValueType == VT_PName) || (targetValueType == VT_Container);
+            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code) || (targetValueType == VT_Num)    ||
+                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date) || (targetValueType == VT_UIDRef) ||
+                     (targetValueType == VT_PName)    || (targetValueType == VT_Container);
         }
         /* row 4 of the table */
         else if (relationshipType == RT_hasConceptMod)
@@ -106,24 +106,23 @@ OFBool DSRPlannedImagingAgentAdministrationSRConstraintChecker::checkContentRela
         else if ((relationshipType == RT_hasProperties) &&
             ((sourceValueType == VT_Text) || (sourceValueType == VT_Code) || (sourceValueType == VT_Num)))
         {
-            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code)  || (targetValueType == VT_Num)  ||
-                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date)  || (targetValueType == VT_Time) ||
-                     (targetValueType == VT_UIDRef)   || (targetValueType == VT_PName) || (targetValueType == VT_Container);
+            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code) || (targetValueType == VT_Num)    ||
+                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date) || (targetValueType == VT_UIDRef) ||
+                     (targetValueType == VT_PName)    || (targetValueType == VT_Container);
         }
         /* row 6 of the table */
         else if ((relationshipType == RT_hasProperties) && (sourceValueType == VT_PName))
         {
-            result = (targetValueType == VT_Text)  || (targetValueType == VT_Code) || (targetValueType == VT_DateTime) ||
-                     (targetValueType == VT_Date)  || (targetValueType == VT_Time) || (targetValueType == VT_UIDRef)   ||
-                     (targetValueType == VT_PName);
+            result = (targetValueType == VT_Text) || (targetValueType == VT_Code)   || (targetValueType == VT_DateTime) ||
+                     (targetValueType == VT_Date) || (targetValueType == VT_UIDRef) ||(targetValueType == VT_PName);
         }
         /* row 7 of the table */
         else if ((relationshipType == RT_inferredFrom) &&
             ((sourceValueType == VT_Text) || (sourceValueType == VT_Code) || (sourceValueType == VT_Num)))
         {
-            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code)  || (targetValueType == VT_Num)  ||
-                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date)  || (targetValueType == VT_Time) ||
-                     (targetValueType == VT_UIDRef)   || (targetValueType == VT_PName) || (targetValueType == VT_Container);
+            result = (targetValueType == VT_Text)     || (targetValueType == VT_Code) || (targetValueType == VT_Num)    ||
+                     (targetValueType == VT_DateTime) || (targetValueType == VT_Date) || (targetValueType == VT_UIDRef) ||
+                     (targetValueType == VT_PName)    || (targetValueType == VT_Container);
         }
     }
     return result;
diff --git a/dcmsr/libsrc/dsrrsdcc.cc b/dcmsr/libsrc/dsrrsdcc.cc
new file mode 100644 (file)
index 0000000..b072562
--- /dev/null
@@ -0,0 +1,96 @@
+/*
+ *
+ *  Copyright (C) 2020, J. Riesmeier, Oldenburg, Germany
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation are maintained by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module: dcmsr
+ *
+ *  Author: Joerg Riesmeier
+ *
+ *  Purpose:
+ *    classes: DSRRenditionSelectionDocumentConstraintChecker
+ *
+ */
+
+
+#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
+
+#include "dcmtk/dcmsr/dsrrsdcc.h"
+
+
+DSRRenditionSelectionDocumentConstraintChecker::DSRRenditionSelectionDocumentConstraintChecker()
+  : DSRIODConstraintChecker()
+{
+}
+
+
+DSRRenditionSelectionDocumentConstraintChecker::~DSRRenditionSelectionDocumentConstraintChecker()
+{
+}
+
+
+OFBool DSRRenditionSelectionDocumentConstraintChecker::isByReferenceAllowed() const
+{
+    return OFFalse;
+}
+
+
+OFBool DSRRenditionSelectionDocumentConstraintChecker::isTemplateSupportRequired() const
+{
+    return OFTrue;
+}
+
+
+OFCondition DSRRenditionSelectionDocumentConstraintChecker::getRootTemplateIdentification(OFString &templateIdentifier,
+                                                                                          OFString &mappingResource) const
+{
+    templateIdentifier = "2010";
+    mappingResource = "DCMR";
+    return EC_Normal;
+}
+
+
+DSRTypes::E_DocumentType DSRRenditionSelectionDocumentConstraintChecker::getDocumentType() const
+{
+    return DT_RenditionSelectionDocument;
+}
+
+
+OFBool DSRRenditionSelectionDocumentConstraintChecker::checkContentRelationship(const E_ValueType sourceValueType,
+                                                                                const E_RelationshipType relationshipType,
+                                                                                const E_ValueType targetValueType,
+                                                                                const OFBool byReference) const
+{
+    /* the following code implements the constraints of table A.35.21-2 in DICOM PS3.3 */
+    OFBool result = OFFalse;
+    /* by-reference relationships not allowed at all */
+    if (!byReference)
+    {
+        /* row 1 of the table */
+        if ((relationshipType == RT_contains) && (sourceValueType == VT_Container))
+        {
+            result = (targetValueType == VT_Text) || (targetValueType == VT_Image) ||
+                     (targetValueType == VT_Waveform) || (targetValueType == VT_Composite);
+        }
+        /* row 2 of the table */
+        else if ((relationshipType == RT_hasObsContext) && (sourceValueType == VT_Container))
+        {
+            result = (targetValueType == VT_Text) || (targetValueType == VT_Code) ||
+                     (targetValueType == VT_UIDRef) || (targetValueType == VT_PName);
+        }
+        /* row 3 of the table */
+        else if ((relationshipType == RT_hasConceptMod) && (sourceValueType == VT_Container))
+        {
+            result = (targetValueType == VT_Code);
+        }
+    }
+    return result;
+}
index e2d7facb10f733913bbd57517dedbc60b3690f91..b0b8cd5e61df685988145076d2558e203b3c26ff 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2000-2019, OFFIS e.V.
+ *  Copyright (C) 2000-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -59,6 +59,7 @@
 #include "dcmtk/dcmsr/dsrprdcc.h"
 #include "dcmtk/dcmsr/dsrpficc.h"
 #include "dcmtk/dcmsr/dsrplicc.h"
+#include "dcmtk/dcmsr/dsrrsdcc.h"
 
 #include "dcmtk/dcmdata/dcuid.h"
 #include "dcmtk/dcmdata/dcvrda.h"
@@ -320,30 +321,32 @@ makeOFConditionConst(SR_EC_CannotProcessIncludedTemplates,      OFM_dcmsr, 34, O
 const size_t EM_EnhancedEquipment = 1 << 0;
 const size_t EM_Timezone          = 1 << 1;
 const size_t EM_Synchronization   = 1 << 2;
+const size_t EM_KeyObjectDocument = 1 << 3;
 
 static const S_DocumentTypeNameMap DocumentTypeNameMap[] =
 {
-    {DSRTypes::DT_invalid,                               "",                                               0,                                         "",   "invalid document type"},
-    {DSRTypes::DT_BasicTextSR,                           UID_BasicTextSRStorage,                           0,                                         "SR", "Basic Text SR"},
-    {DSRTypes::DT_EnhancedSR,                            UID_EnhancedSRStorage,                            0,                                         "SR", "Enhanced SR"},
-    {DSRTypes::DT_ComprehensiveSR,                       UID_ComprehensiveSRStorage,                       0,                                         "SR", "Comprehensive SR"},
-    {DSRTypes::DT_KeyObjectSelectionDocument,            UID_KeyObjectSelectionDocumentStorage,            0,                                         "KO", "Key Object Selection Document"},
-    {DSRTypes::DT_MammographyCadSR,                      UID_MammographyCADSRStorage,                      0,                                         "SR", "Mammography CAD SR"},
-    {DSRTypes::DT_ChestCadSR,                            UID_ChestCADSRStorage,                            0,                                         "SR", "Chest CAD SR"},
-    {DSRTypes::DT_ColonCadSR,                            UID_ColonCADSRStorage,                            EM_EnhancedEquipment,                      "SR", "Colon CAD SR"},
-    {DSRTypes::DT_ProcedureLog,                          UID_ProcedureLogStorage,                          EM_Synchronization,                        "SR", "Procedure Log"},
-    {DSRTypes::DT_XRayRadiationDoseSR,                   UID_XRayRadiationDoseSRStorage,                   EM_EnhancedEquipment,                      "SR", "X-Ray Radiation Dose SR"},
-    {DSRTypes::DT_SpectaclePrescriptionReport,           UID_SpectaclePrescriptionReportStorage,           EM_EnhancedEquipment,                      "SR", "Spectacle Prescription Report"},
-    {DSRTypes::DT_MacularGridThicknessAndVolumeReport,   UID_MacularGridThicknessAndVolumeReportStorage,   EM_EnhancedEquipment,                      "SR", "Macular Grid Thickness and Volume Report"},
-    {DSRTypes::DT_ImplantationPlanSRDocument,            UID_ImplantationPlanSRDocumentStorage,            EM_EnhancedEquipment,                      "SR", "Implantation Plan SR Document"},
-    {DSRTypes::DT_Comprehensive3DSR,                     UID_Comprehensive3DSRStorage,                     0,                                         "SR", "Comprehensive 3D SR"},
-    {DSRTypes::DT_RadiopharmaceuticalRadiationDoseSR,    UID_RadiopharmaceuticalRadiationDoseSRStorage,    EM_EnhancedEquipment,                      "SR", "Radiopharmaceutical Radiation Dose SR"},
-    {DSRTypes::DT_ExtensibleSR,                          UID_ExtensibleSRStorage,                          EM_EnhancedEquipment,                      "SR", "Extensible SR"},
-    {DSRTypes::DT_AcquisitionContextSR,                  UID_AcquisitionContextSRStorage,                  EM_EnhancedEquipment,                      "SR", "Acquisition Context SR"},
-    {DSRTypes::DT_SimplifiedAdultEchoSR,                 UID_SimplifiedAdultEchoSRStorage,                 EM_EnhancedEquipment | EM_Timezone,        "SR", "Simplified Adult Echo SR"},
-    {DSRTypes::DT_PatientRadiationDoseSR,                UID_PatientRadiationDoseSRStorage,                EM_EnhancedEquipment,                      "SR", "Patient Radiation Dose SR"},
-    {DSRTypes::DT_PerformedImagingAgentAdministrationSR, UID_PerformedImagingAgentAdministrationSRStorage, EM_EnhancedEquipment | EM_Synchronization, "SR", "Performed Imaging Agent Administration SR"},
-    {DSRTypes::DT_PlannedImagingAgentAdministrationSR,   UID_PlannedImagingAgentAdministrationSRStorage,   EM_EnhancedEquipment,                      "SR", "Planned Imaging Agent Administration SR"}
+    {DSRTypes::DT_invalid,                               "",                                                  0,                                                                "",   "invalid document type"},
+    {DSRTypes::DT_BasicTextSR,                           UID_BasicTextSRStorage,                              0,                                                                "SR", "Basic Text SR"},
+    {DSRTypes::DT_EnhancedSR,                            UID_EnhancedSRStorage,                               0,                                                                "SR", "Enhanced SR"},
+    {DSRTypes::DT_ComprehensiveSR,                       UID_ComprehensiveSRStorage,                          0,                                                                "SR", "Comprehensive SR"},
+    {DSRTypes::DT_KeyObjectSelectionDocument,            UID_KeyObjectSelectionDocumentStorage,               EM_KeyObjectDocument,                                             "KO", "Key Object Selection Document"},
+    {DSRTypes::DT_MammographyCadSR,                      UID_MammographyCADSRStorage,                         0,                                                                "SR", "Mammography CAD SR"},
+    {DSRTypes::DT_ChestCadSR,                            UID_ChestCADSRStorage,                               0,                                                                "SR", "Chest CAD SR"},
+    {DSRTypes::DT_ColonCadSR,                            UID_ColonCADSRStorage,                               EM_EnhancedEquipment,                                             "SR", "Colon CAD SR"},
+    {DSRTypes::DT_ProcedureLog,                          UID_ProcedureLogStorage,                             EM_Synchronization,                                               "SR", "Procedure Log"},
+    {DSRTypes::DT_XRayRadiationDoseSR,                   UID_XRayRadiationDoseSRStorage,                      EM_EnhancedEquipment,                                             "SR", "X-Ray Radiation Dose SR"},
+    {DSRTypes::DT_SpectaclePrescriptionReport,           UID_SpectaclePrescriptionReportStorage,              EM_EnhancedEquipment,                                             "SR", "Spectacle Prescription Report"},
+    {DSRTypes::DT_MacularGridThicknessAndVolumeReport,   UID_MacularGridThicknessAndVolumeReportStorage,      EM_EnhancedEquipment,                                             "SR", "Macular Grid Thickness and Volume Report"},
+    {DSRTypes::DT_ImplantationPlanSRDocument,            UID_ImplantationPlanSRDocumentStorage,               EM_EnhancedEquipment,                                             "SR", "Implantation Plan SR Document"},
+    {DSRTypes::DT_Comprehensive3DSR,                     UID_Comprehensive3DSRStorage,                        0,                                                                "SR", "Comprehensive 3D SR"},
+    {DSRTypes::DT_RadiopharmaceuticalRadiationDoseSR,    UID_RadiopharmaceuticalRadiationDoseSRStorage,       EM_EnhancedEquipment,                                             "SR", "Radiopharmaceutical Radiation Dose SR"},
+    {DSRTypes::DT_ExtensibleSR,                          UID_ExtensibleSRStorage,                             EM_EnhancedEquipment,                                             "SR", "Extensible SR"},
+    {DSRTypes::DT_AcquisitionContextSR,                  UID_AcquisitionContextSRStorage,                     EM_EnhancedEquipment,                                             "SR", "Acquisition Context SR"},
+    {DSRTypes::DT_SimplifiedAdultEchoSR,                 UID_SimplifiedAdultEchoSRStorage,                    EM_EnhancedEquipment | EM_Timezone,                               "SR", "Simplified Adult Echo SR"},
+    {DSRTypes::DT_PatientRadiationDoseSR,                UID_PatientRadiationDoseSRStorage,                   EM_EnhancedEquipment,                                             "SR", "Patient Radiation Dose SR"},
+    {DSRTypes::DT_PerformedImagingAgentAdministrationSR, UID_PerformedImagingAgentAdministrationSRStorage,    EM_EnhancedEquipment | EM_Synchronization,                        "SR", "Performed Imaging Agent Administration SR"},
+    {DSRTypes::DT_PlannedImagingAgentAdministrationSR,   UID_PlannedImagingAgentAdministrationSRStorage,      EM_EnhancedEquipment,                                             "SR", "Planned Imaging Agent Administration SR"},
+    {DSRTypes::DT_RenditionSelectionDocument,            UID_RenditionSelectionDocumentRealTimeCommunication, EM_EnhancedEquipment | EM_Synchronization | EM_KeyObjectDocument, "KO", "Rendition Selection Document"}
 };
 
 
@@ -584,6 +587,36 @@ OFBool DSRTypes::requiresSynchronizationModule(const E_DocumentType documentType
 }
 
 
+OFBool DSRTypes::usesSRDocumentSeriesModule(const E_DocumentType documentType)
+{
+    /* SR Document Series Module and Key Object Document Series Module are mutually exclusive */
+    return !usesKeyObjectDocumentSeriesModule(documentType);
+}
+
+
+OFBool DSRTypes::usesKeyObjectDocumentSeriesModule(const E_DocumentType documentType)
+{
+    /* Key Object Document Series Module is used if (and only if) Key Object Document Module is used */
+    return usesKeyObjectDocumentModule(documentType);
+}
+
+
+OFBool DSRTypes::usesSRDocumentGeneralModule(const E_DocumentType documentType)
+{
+    /* SR Document Module and Key Object Document Module are mutually exclusive */
+    return !usesKeyObjectDocumentModule(documentType);
+}
+
+
+OFBool DSRTypes::usesKeyObjectDocumentModule(const E_DocumentType documentType)
+{
+    const S_DocumentTypeNameMap *iterator = DocumentTypeNameMap;
+    while ((iterator->Type != DT_last) && (iterator->Type != documentType))
+        iterator++;
+    return (iterator->ExtendedModules & EM_KeyObjectDocument) > 0;
+}
+
+
 const char *DSRTypes::relationshipTypeToDefinedTerm(const E_RelationshipType relationshipType)
 {
     const S_RelationshipTypeNameMap *iterator = RelationshipTypeNameMap;
@@ -1519,6 +1552,9 @@ DSRIODConstraintChecker *DSRTypes::createIODConstraintChecker(const E_DocumentTy
         case DT_PlannedImagingAgentAdministrationSR:
             checker = new DSRPlannedImagingAgentAdministrationSRConstraintChecker();
             break;
+        case DT_RenditionSelectionDocument:
+            checker = new DSRRenditionSelectionDocumentConstraintChecker();
+            break;
         case DT_invalid:
             /* nothing to do */
             break;
index 949da6371ce74232a576295551637b81aea8a40a..3b0613a2e93d6c055b6759786d7eb06f65edaffe 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2000-2019, OFFIS e.V.
+ *  Copyright (C) 2000-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -261,7 +261,7 @@ OFCondition DSRWaveformReferenceValue::checkSOPClassUID(const OFString &sopClass
     OFCondition result = DSRCompositeReferenceValue::checkSOPClassUID(sopClassUID);
     if (result.good())
     {
-        /* check for all valid/known SOP classes (according to DICOM PS 3.6-2017e) */
+        /* check for all valid/known SOP classes (according to DICOM PS 3.6-2020c) */
         if ((sopClassUID != UID_TwelveLeadECGWaveformStorage) &&
             (sopClassUID != UID_GeneralECGWaveformStorage) &&
             (sopClassUID != UID_AmbulatoryECGWaveformStorage) &&
@@ -270,7 +270,13 @@ OFCondition DSRWaveformReferenceValue::checkSOPClassUID(const OFString &sopClass
             (sopClassUID != UID_BasicVoiceAudioWaveformStorage) &&
             (sopClassUID != UID_GeneralAudioWaveformStorage) &&
             (sopClassUID != UID_ArterialPulseWaveformStorage) &&
-            (sopClassUID != UID_RespiratoryWaveformStorage))
+            (sopClassUID != UID_RespiratoryWaveformStorage) &&
+            (sopClassUID != UID_MultichannelRespiratoryWaveformStorage) &&
+            (sopClassUID != UID_RoutineScalpElectroencephalogramWaveformStorage) &&
+            (sopClassUID != UID_ElectromyogramWaveformStorage) &&
+            (sopClassUID != UID_ElectrooculogramWaveformStorage) &&
+            (sopClassUID != UID_SleepElectroencephalogramWaveformStorage) &&
+            (sopClassUID != UID_BodyPositionWaveformStorage))
         {
             result = SR_EC_InvalidValue;
         }
index c0ec0821718f2d047e7bb4939e185ebcfc16ee07..8fba9f5c2ce54ac8fd90b62d00d69450d9d5bf42 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -27,6 +27,7 @@
 
 #include "dcmtk/dcmdata/dcdeftag.h"
 #include "dcmtk/dcmdata/dcdatset.h"
+#include "dcmtk/dcmdata/dcdict.h"
 
 #include "dcmtk/dcmsr/dsrdoc.h"
 #include "dcmtk/dcmsr/dsrnumvl.h"
@@ -273,6 +274,13 @@ OFTEST(dcmsr_TID1411_VolumetricROIMeasurements)
 
 OFTEST(dcmsr_TID1500_MeasurementReport)
 {
+    /* make sure data dictionary is loaded */
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
     TID1500_MeasurementReport report(CMR_CID7021::ImagingMeasurementReport);
     DSRCodedEntryValue title;
     /* check initial settings */
@@ -486,6 +494,13 @@ OFTEST(dcmsr_TID1501_MeasurementGroup)
 
 OFTEST(dcmsr_TID1600_ImageLibrary)
 {
+    /* make sure data dictionary is loaded */
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
     TID1600_ImageLibrary library;
     DcmItem *item1, *item2;
     /* check template identification */
index 1155d8e253b5dd0e8bb9f89c52630e9ca0cb5d7f..0a0e534a9363df4db17954a65d8b9fecc60be07a 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2015-2019, J. Riesmeier, Oldenburg, Germany
+ *  Copyright (C) 2015-2020, J. Riesmeier, Oldenburg, Germany
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -27,6 +27,7 @@
 
 #include "dcmtk/dcmdata/dcdeftag.h"
 #include "dcmtk/dcmdata/dcdatset.h"
+#include "dcmtk/dcmdata/dcdict.h"
 
 #include "dcmtk/dcmsr/dsrcodvl.h"
 
@@ -39,6 +40,7 @@ OFTEST(dcmsr_validCompleteOrEmptyCode)
     const DSRCodedEntryValue code3("a little too long\\with VM>1", "99TEST", "some invalid test code", DSRTypes::CVT_Short, OFFalse /*check*/);
     const DSRCodedEntryValue code4("", "", "");
     const DSRCodedEntryValue code5("urn:0817", "" /* empty coding scheme designator */, "some other code");
+    const DSRCodedEntryValue code6("urn:0817", "" /* empty coding scheme designator */, "1.0" /* non-empty coding scheme version */, "some other code", DSRTypes::CVT_URN, OFFalse /*check*/);
     /* then, perform some tests with these codes */
     OFCHECK(code1.isValid());
     OFCHECK(code1.isComplete());
@@ -55,6 +57,9 @@ OFTEST(dcmsr_validCompleteOrEmptyCode)
     OFCHECK(code5.isValid());
     OFCHECK(code5.isComplete());
     OFCHECK(!code5.isEmpty());
+    OFCHECK(!code6.isValid());
+    OFCHECK(code6.isComplete());
+    OFCHECK(!code6.isEmpty());
 }
 
 
@@ -99,6 +104,13 @@ OFTEST(dcmsr_determineCodeValueType)
 
 OFTEST(dcmsr_writeCodeSequence)
 {
+    /* make sure data dictionary is loaded */
+    if (!dcmDataDict.isDictionaryLoaded())
+    {
+        OFCHECK_FAIL("no data dictionary loaded, check environment variable: " DCM_DICT_ENVIRONMENT_VARIABLE);
+        return;
+    }
+
     DcmDataset dataset;
     /* first, try the standard case (short code value) */
     DSRCodedEntryValue codedEntry("121206", "DCM", "Distance", DSRTypes::CVT_Short);
index d40200d5419333b4f2aa63c7f032aa1e065095fe..d3248235b929989afa27bc222dd3bad25e85d3f9 100644 (file)
@@ -5,6 +5,6 @@ project(dcmtls)
 include_directories("${dcmtls_SOURCE_DIR}/include" "${ofstd_SOURCE_DIR}/include" "${oflog_SOURCE_DIR}/include" "${dcmdata_SOURCE_DIR}/include" "${dcmnet_SOURCE_DIR}/include" ${ZLIB_INCDIR} ${OPENSSL_INCDIR})
 
 # recurse into subdirectories
-foreach(SUBDIR libsrc include docs)
+foreach(SUBDIR libsrc include docs tests)
   add_subdirectory(${SUBDIR})
 endforeach()
index c1d3d15da0c961426a6da34945776230b8a325e0..e20de23ab55e86cb45633c7c5e5840f8e9bcf3d8 100644 (file)
@@ -1,6 +1,6 @@
-=============================================================================
+============================================================
 CERTIFICATION AUTHORITY (CA) CERTIFICATE MANAGEMENT IN DCMTK
-=============================================================================
+============================================================
 
 All tools in DCMTK that support TLS encrypted network connections
 need to have a list of trusted certificates (typically CA certificates)
@@ -12,10 +12,11 @@ file-based and directory-based. The command line tools in DCMTK
 offer the following command line options for this purpose:
 
   certification authority:
-    +cf   --add-cert-file        [c]ertificate filename: string
-                                 add certificate file to list of certificates
-    +cd   --add-cert-dir         [c]ertificate directory: string
-                                 add certificates in d to list of certificates
+    +cf   --add-cert-file  [f]ilename: string
+            add certificate file to list of certificates
+
+    +cd   --add-cert-dir  [d]irectory: string
+            add certificates in d to list of certificates
 
 When using DCMTK at library level, the methods corresponding to these
 command line options are DcmTransportLayer::addTrustedCertificateFile()
index c99cc2d78806a9d1a42d515e063459758fecfd48..ee6dffdd511ca198955be4a76605094d49b033b3 100644 (file)
@@ -14,6 +14,7 @@ The main interface classes are:
 \section Files
 
 The following files provide further documentation:
+\li \ref file_certstor
 \li \ref file_ciphers
 \li \ref file_randseed
 
@@ -59,6 +60,11 @@ ASC_setTransportLayerType(params, 1);
 
 */
 
+/*!
+    \page file_certstor certstor.txt file
+    \verbinclude certstor.txt
+*/
+
 /*!
     \page file_ciphers ciphers.txt file
     \verbinclude ciphers.txt
index 153be7d175ca9c9148ff5b9a3b4e5c7351165d70..3788d465bb0419b32ab5b60032ae5b3b7e78fd44 100644 (file)
@@ -309,27 +309,27 @@ tlsscu.o: tlsscu.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../../dcmnet/include/dcmtk/dcmnet/dcompat.h \
- ../../ofstd/include/dcmtk/ofstd/ofbmanip.h \
+ ../../dcmnet/include/dcmtk/dcmnet/dcasccff.h \
  ../../dcmnet/include/dcmtk/dcmnet/dndefine.h \
- ../../dcmnet/include/dcmtk/dcmnet/dimse.h \
+ ../../dcmnet/include/dcmtk/dcmnet/dcasccfg.h \
+ ../../dcmnet/include/dcmtk/dcmnet/assoc.h \
  ../../dcmnet/include/dcmtk/dcmnet/dicom.h \
  ../../dcmnet/include/dcmtk/dcmnet/cond.h \
  ../../ofstd/include/dcmtk/ofstd/ofconsol.h \
+ ../../dcmnet/include/dcmtk/dcmnet/dcompat.h \
+ ../../ofstd/include/dcmtk/ofstd/ofbmanip.h \
  ../../dcmnet/include/dcmtk/dcmnet/lst.h \
  ../../dcmnet/include/dcmtk/dcmnet/dul.h \
  ../../dcmnet/include/dcmtk/dcmnet/extneg.h \
  ../../dcmnet/include/dcmtk/dcmnet/dcuserid.h \
  ../../dcmnet/include/dcmtk/dcmnet/dntypes.h \
- ../../dcmnet/include/dcmtk/dcmnet/assoc.h \
- ../../dcmnet/include/dcmtk/dcmnet/dcasccff.h \
- ../../dcmnet/include/dcmtk/dcmnet/dcasccfg.h \
  ../../dcmnet/include/dcmtk/dcmnet/dccftsmp.h \
  ../../dcmnet/include/dcmtk/dcmnet/dccfuidh.h \
  ../../dcmnet/include/dcmtk/dcmnet/dccfpcmp.h \
  ../../dcmnet/include/dcmtk/dcmnet/dccfrsmp.h \
  ../../dcmnet/include/dcmtk/dcmnet/dccfenmp.h \
  ../../dcmnet/include/dcmtk/dcmnet/dccfprmp.h \
+ ../../dcmnet/include/dcmtk/dcmnet/dimse.h \
  ../include/dcmtk/dcmtls/tlstrans.h \
  ../../dcmnet/include/dcmtk/dcmnet/dcmtrans.h \
  ../../dcmnet/include/dcmtk/dcmnet/dcmlayer.h \
index 5fc8fd77ffb7aed01a50ee5bf97227b269695231..b9fa2a8a7d0c34ebf4a8eb15108fe8bdb380583c 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2017-2019, OFFIS e.V.
+ *  Copyright (C) 2017-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -83,9 +83,9 @@ void DcmTLSOptions::addTLSCommandlineOptions(OFCommandLine& cmd)
       cmd.addOption("--pem-keys",           "-pem",    "read keys and certificates as PEM file (default)");
       cmd.addOption("--der-keys",           "-der",    "read keys and certificates as DER file");
     cmd.addSubGroup("certification authority:");
-      cmd.addOption("--add-cert-file",      "+cf",  1, "[c]ertificate filename: string",
+      cmd.addOption("--add-cert-file",      "+cf",  1, "[f]ilename: string",
                                                        "add certificate file to list of certificates");
-      cmd.addOption("--add-cert-dir",       "+cd",  1, "[c]ertificate directory: string",
+      cmd.addOption("--add-cert-dir",       "+cd",  1, "[d]irectory: string",
                                                        "add certificates in d to list of certificates");
     cmd.addSubGroup("security profile:");
       cmd.addOption("--profile-bcp195",     "+px",     "BCP 195 TLS Profile (default)");
index 8ee25285d4c80c15c549a6fec86b5b8574efca82..c4d833979cfc0d9726f05fd6a1b3aab75a9fba1e 100644 (file)
@@ -92,6 +92,22 @@ OFCondition DcmTLSSCU::initNetwork()
     return EC_IllegalCall; // TODO: need to find better error code
   }
 
+  /* Add trusted certificates from files and directories
+   */
+  OFListIterator(OFString) certFile = m_trustedCertFiles.begin();
+  while (certFile != m_trustedCertFiles.end())
+  {
+    if (TCS_ok != m_tLayer->addTrustedCertificateFile( (*certFile).c_str(), m_certKeyFileFormat))
+      DCMNET_WARN("Unable to load certificate file '" << *certFile << "', ignoring");
+    certFile++;
+  }
+  OFListIterator(OFString) certDir = m_trustedCertDirs.begin();
+  while (certDir != m_trustedCertDirs.end())
+  {
+    if (TCS_ok != m_tLayer->addTrustedCertificateDir( (*certDir).c_str(), m_certKeyFileFormat))
+      DCMNET_WARN("Unable to load certificates from directory '" << *certDir<< "', ignoring");
+  }
+
   /* If authentication of both sides (and not only encryption) is desired,
    * handle all associated parameters
    */
diff --git a/dcmtls/tests/CMakeLists.txt b/dcmtls/tests/CMakeLists.txt
new file mode 100644 (file)
index 0000000..0d8c7d2
--- /dev/null
@@ -0,0 +1,8 @@
+# declare executables
+DCMTK_ADD_EXECUTABLE(dcmtls_tests tests tscuscptls)
+
+# make sure executables are linked to the corresponding libraries
+DCMTK_TARGET_LINK_MODULES(dcmtls_tests dcmnet dcmtls)
+
+# This macro parses tests.cc and registers all tests
+DCMTK_ADD_TESTS(dcmtls)
diff --git a/dcmtls/tests/tests.cc b/dcmtls/tests/tests.cc
new file mode 100644 (file)
index 0000000..41bb184
--- /dev/null
@@ -0,0 +1,28 @@
+/*
+ *
+ *  Copyright (C) 2019-2020, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmtls
+ *
+ *  Authors:  Michel Amat, Damien Lerat
+ *
+ *  Purpose: main test program
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"
+#include "dcmtk/ofstd/oftest.h"
+
+OFTEST_REGISTER(dcmtls_scp_tls);
+OFTEST_REGISTER(dcmtls_scp_pool_tls);
+
+OFTEST_MAIN("dcmtls")
diff --git a/dcmtls/tests/tscuscptls.cc b/dcmtls/tests/tscuscptls.cc
new file mode 100644 (file)
index 0000000..ef0cb22
--- /dev/null
@@ -0,0 +1,462 @@
+/*
+ *
+ *  Copyright (C) 2019-2020, OFFIS e.V.
+ *  All rights reserved.  See COPYRIGHT file for details.
+ *
+ *  This software and supporting documentation were developed by
+ *
+ *    OFFIS e.V.
+ *    R&D Division Health
+ *    Escherweg 2
+ *    D-26121 Oldenburg, Germany
+ *
+ *
+ *  Module:  dcmtls
+ *
+ *  Authors:  Michel Amat, Damien Lerat
+ *
+ *  Purpose: TLS test for classes DcmSCP and DcmSCPPool
+ *
+ *  Note: This test will fail after 2029-02-25 due to certificate expiry. 
+ *        The keys embedded in this file should be replaced then (see below).
+ *
+ */
+
+#include "dcmtk/config/osconfig.h"    /* make sure OS specific configuration is included first */
+
+#define INCLUDE_CMATH
+#include "dcmtk/ofstd/ofstdinc.h"
+#include "dcmtk/ofstd/oftest.h"
+#include "dcmtk/ofstd/oftimer.h"
+#include "dcmtk/oflog/consap.h"
+#include "dcmtk/dcmnet/scp.h"
+#include "dcmtk/dcmnet/scu.h"
+#include "dcmtk/dcmnet/scppool.h"
+#include "dcmtk/dcmnet/dcmlayer.h"
+#include "dcmtk/dcmtls/tlsscu.h"
+
+#ifdef WITH_THREADS
+
+/** Method that ensures that the current thread is actually sleeping for the
+ *  defined number of seconds (at least).
+ *  The problem with the regular sleep() function called from OFStandard::sleep
+ *  is that it might be interrupted by signals or a network timeout (depending
+ *  on the operating system). This methods re-executes OFStandard's sleep method
+ *  until the desired number of seconds have elapsed.
+ *  @param sleep The number of seconds to sleep (at least)
+ */
+static void force_sleep(Uint32 sleep)
+{
+    OFTimer timer;
+    double elapsed = timer.getDiff();
+    while (elapsed < (double)sleep)
+    {
+        // Use ceiling since otherwise we could wait too short
+        OFStandard::sleep(OFstatic_cast(unsigned int, ceil(sleep-elapsed)));
+        elapsed = timer.getDiff();
+    }
+}
+
+
+/** TestSCP derived from DcmSCP in order to test TLS functionality
+ *  through function setTransportLayer of DcmSCPConfig.
+ *
+ *  Additionally the SCP derives from OFThread in order to construct the
+ *  test case (i.e. send data with SCU at the same time and check results).
+ */
+struct TestSCP: DcmSCP, OFThread
+{
+    /** Constructor
+     */
+    TestSCP() :
+        DcmSCP(),
+        m_listen_result(EC_NotYetImplemented), // value indicating "not set"
+        m_set_stop_after_assoc(OFFalse),
+        m_set_stop_after_timeout(OFFalse)
+    {
+    }
+
+    /** Clear settings
+     */
+    void clear()
+    {
+        m_listen_result = EC_NotYetImplemented;
+        m_set_stop_after_assoc = OFFalse;
+        m_set_stop_after_timeout = OFFalse;
+    }
+
+    /** Overwrite method from DcmSCP in order to test feature to stop after current
+     *  association.
+     *  @return Returns value of m_set_stop_after_assoc
+     */
+    virtual OFBool stopAfterCurrentAssociation()
+    {
+        return m_set_stop_after_assoc;
+    }
+
+    /** Overwrite method from DcmSCP in order to test feature to stop after
+    *   the SCP's connection timeout occurred in non-blocking mode.
+    *   @return Returns value of m_set_stop_after_timeout
+    */
+    virtual OFBool stopAfterConnectionTimeout()
+    {
+        return m_set_stop_after_timeout;
+    }
+
+    /// The result returned my SCP's listen() method
+    OFCondition m_listen_result;
+    /// If set, the SCP should stop after the currently running association
+    OFBool m_set_stop_after_assoc;
+    /// If set, the SCP should stop after TCP timeout occurred in non-blocking mode
+    OFBool m_set_stop_after_timeout;
+
+    /** Method called by OFThread to start SCP operation. Starts listen() loop of DcmSCP.
+    */
+    virtual void run()
+    {
+        m_listen_result = listen();
+    }
+
+};
+
+// -------------- End of class TestSCP -------------------------
+
+struct TestPool : DcmSCPPool<>, OFThread
+{
+    OFCondition result;
+protected:
+    void run()
+    {
+        result = listen();
+    }
+};
+
+// -------------- End of class TestPool -------------------------
+
+#ifdef WITH_OPENSSL
+
+struct TestTLSSCU : DcmTLSSCU, OFThread
+{
+    OFCondition result;
+protected:
+    void run()
+    {
+        OFCHECK(negotiateAssociation().good());
+        result = sendECHORequest(0);
+        releaseAssociation();
+    }
+};
+
+// -------------- End of class TestTLSSCU -------------------------
+
+
+#define PRIVATE_KEY_FILENAME "privkey.pem"
+#define PUBLIC_SELFSIGNED_CERT_FILENAME "pubselfsignedcert.pem"
+#define PRIVATE_KEY_PWD "testDcmtk!"
+
+
+/** Method write_temp_key_cert_files writes private key and public certificate files,
+ *  needed by tests dcmtls_scp_tls and dcmtls_scp_pool_tls.
+ *  It corresponds to the files generated by the following openssl command>
+ *  > openssl req -x509 -newkey rsa:4096 -keyout PRIVATE_KEY_FILENAME  -passout pass:PRIVATE_KEY_PWD
+ *    -out PUBLIC_SELFSIGNED_CERT_FILENAME -days 3653 -subj "/C=DE/ST=DcmTls/L=Tests/O=OFFIS/OU=DCMTK/CN=dicom@offis.de"
+ *  @note The certificate will expire on 2029-02-25. The keys should be replaced then.
+ */
+void write_temp_key_cert_files()
+{
+    const char * privKey="-----BEGIN ENCRYPTED PRIVATE KEY-----\n"
+"MIIJnDBOBgkqhkiG9w0BBQ0wQTApBgkqhkiG9w0BBQwwHAQIfH2W1N63B6wCAggA\n"
+"MAwGCCqGSIb3DQIJBQAwFAYIKoZIhvcNAwcECPvpj/Xqx43SBIIJSHU3VPzHDKNX\n"
+"8c7vnHT1OYjeBkx6EsnzewuWIhnzDFdt1SOXgIGUZrXVcxln1t0TvyZug+zEPY7L\n"
+"TxQy/pT3N81coXzFF+Pj67wOVSVOZNtoEJIPzDvKYzTHhtX40TUK8R1rLyArMD6P\n"
+"cODkY+pBUOhd9BlRr1tkaMv0GTAjxv+OhJuI/hothmRtyiZelTitxb4eHRD9ycbP\n"
+"bGu3nmTf/MgcPohL/PUV9PIruRGMImQN8XDrP6Ekkp5HWi4OBkZcj37fM6N6/RZ7\n"
+"fB8Mc1ebk7sRlssSoiw5LNpAz8M+geUjwTljU3rGTS/KnCMVmvcsnbMahqIrTzub\n"
+"I3SPfxHKm5WjeBXDlTBONMGvEzKKXYoAV6XWKkvLClhkp+oQweOAzzHk/SJJYU7s\n"
+"wmnfGGrkG26HDE0sYP5BTFI6wipnWXcLmXVVN8cawqh74Tfc3HZR0KNEiIb0nox+\n"
+"zWsXYHf7OVEyj72R+Vho77PcKHDsyYNdm++VwZlESbvzZkwyZRqzrzx7o93cODK+\n"
+"GIrvOIHVJ6qW3U/mkLh4RG+XjZimJ1ksK3HIwQirtDrOuvHi+GaBSgp7R5niOkA+\n"
+"0PIJ4FzuBvRyXLPmSZlgo5eaGs+JrdYQSLgmiXAEmlm/200u3xtW3la6FhZyR6Mc\n"
+"moNdW4B+G/0Ra4KFVv/2GCT2vGHT+5bbnpgeviMxn3/k6EtYuoFS9lcHzHrKppwj\n"
+"Xx9ssbSR2SgoBSuxM4/69KzkIb0Ow7Sxex7lFt7q01Qtr26Iz4lioiaozMmow362\n"
+"4XQsYck8eLakC5Ygmh5hCUpD0GtdY3n+8DT9OTfUFAE8k3PHjNRTI2SPs4F4Nlbf\n"
+"WSOmBnQHb3/TD39VaqLhmJMAdax3izSnjk3ePg1JKhVJnGo6saYa8iYNZgbRn1/2\n"
+"Xk4++UZVGaiorRHYpXx8UcNSdGkJpE6wqki5zbUhk0YtvzYC54DA260G0aZW0BEp\n"
+"PTyhLnPW4OZWJwG3rwYC11DYees030WA0gCfwess3MP+fmZQfGMIZioAG2WVMgIl\n"
+"yys4HaPb5vQkjTRqTefFEvfAXxKFfFgrnWwlyzsB9A5mglQYyCl7wTQt9FiF4s5q\n"
+"SODDD2Nk72RYJc+JnaARb97OWHUFcmF5MoXJdokEKm2pYa3fcJD1UaBoquufedZY\n"
+"uyjnBXz7DxPV8ZhI9KYAX+3BIo6DedPUb+43WcgNXnyqI5xnX/TWeFt4kCp60WFa\n"
+"Yku3Og7QIy/PTfwXNvG6yP9koOZqANwdroN8bwwS2y3f3oTkhsy0YgcQWlIPGl6d\n"
+"/trbWC2EkNBQOMsE0tRxRnZcP3OOw4pHAPqv71EFUHp9gLxvGb9rMuKqcVEC53xJ\n"
+"omFrlV1x8Pa4GO3t0xg1Jatx4Sly9FOi8KqfFGUiyN1NdPuBw4+gpC9F7i5RpBjW\n"
+"Yrl/mqZizGNtzRNLAESGoVD/LANmVL9SKNPp9tPDsVIWtVcCBfJVietBqq1JyiKX\n"
+"6hdMNaXnAPXv1G95kczGkOjFDIs2lII9ChkY4I6wes0K6n4WbC5kuf3Z/ZAedTdI\n"
+"kpQxbFYi+B/95foQM5MrHXibn+SOAO0DzqfOdG0ymBn0X/oeXbgxENmF/fZqE6Ab\n"
+"MdusaIy3mnut8yQI3t1Tv/Ei2WHmnXM2bTkyd5OGZK5wYYZlMDXVPBXlZ5ZgRDRv\n"
+"zE8hDYp5sXjjDvzVJjMWPj80qcdjY9wvNaoCXpdVHh4zZVgnO9L/r1XrpkIxg9/E\n"
+"H3sihqtpTBs6CIDoMGiKI7dkpRyyILLhxggnpf/OEbUTypaobnZ/sOMEmNw8DGR/\n"
+"/2c6ECr2/j283vifz1tiEV29Y/Pb1emiW0+66Cjoge2DpHmdB+d2va98OQzaT8Z2\n"
+"hBLpIZtELrSZ5DLaVQG/aK5ZS9FxwaWD/Jrj34HJ16cMMSLXH/1eg89XqUaItQ40\n"
+"eGWEWdL7vhdNnhkvUqubOc6y4US3EMGm0oB+72KhlvUwrahI/lzWGlevVjstbVAb\n"
+"WS/Tg5Jf5/tObUe8OxiW4+NXn/4sx5+SZ3uQRqnLOBFNWSgwE/32S4yCZQjRJZrd\n"
+"aNVZybpk5iivH2nKpaA0e0iCTCuqB4ssERspyVeMlnlJ7GSYErq459dkMRWA/JtP\n"
+"C9LM1iBwcZ+RgG0Rot1xWmrsjbf8DbPhCj1GqLOBJ82ehw6uKVrE2njr03aRe3yl\n"
+"4oOmtrU0TwqPOW7B/8wrwLd9s/1cIxVt7YTzTuiS7f6PL6ec/d0txyCqotKhjWs3\n"
+"arWskJoUoY5A1+yD8RU5QpG/gDuJ+ToPV+GXvds+aXMtTrQKtlkXUWfkd+Z2RxEm\n"
+"ZGw8+pFmm0YW80KGu6qN37F5G2MMlxtpiEIAIBfpEmWZxRMFMdbiQtJuK3o3ApXJ\n"
+"GcXq6qXGXX+u6mBY7VLS1U4Q9PKJJ0/v1PW+0EHA5eeq1J+ZBGhCeM8j9OZzEwRu\n"
+"r66jpdxccd4goh39jyZVEQAPxuDxPXzaDiar7Bxpb5ndef1Ml0SX5fPwZq1k8btH\n"
+"udKrUGptJwinQ+F6tkr2LOJlssJ8dyw+rVrTqV1mP4KMwM/2EOSCfs15gBy7fSg2\n"
+"srybRUgX87hY2KhzBU2+J7VDbWiwFnZ30y05XiVXDx+4KZUlXIWSAUjHBGTTysu0\n"
+"jxEN96vkEWbxzcXCZpg1Q4L2VFfeDurL7D6wbEetwW+5hoiB1k/STyI2MFNxVBUb\n"
+"JSTj/KA3Ki3V9wd+YZrOH7HHn1jTzn8QnoP5xvB/uJ9Sn1AWtmawLchg9D3eVSEX\n"
+"ggQFSbylGhe+aEHnZwUjDtfvjY++CcurnMSLG2pyHxjzeevhtZg8TfJ7AMHdejBA\n"
+"PYnQARJ8Pig7m/D5KNzGaP4i0lQzUMs0+e6UIX82n56Qugy7Wrw2+OV0njG1iDzQ\n"
+"lXaYEFs4DPk4ATPrxFZlNpOW+VjAwU+GrKvYkRu2kYwAz3AdsbBv1Gq3o0vx5EEM\n"
+"36Z13eCtP1N35M9oSFtfh2q7Yu0+xqNZ6Iy4vuxiARp4T7nzv3Q39O+0rC+YDGw3\n"
+"Eh5nzkv/KOALmJSPv2ZLZ/lPH+5DW8Khg9YOJpB1q0CDQCuxBGdY0Sh54G6xPNfk\n"
+"DbepXf+ja9mUcs6u07JXLeSgJjdkwu5Grj2Bbszfn7fL2fjoZgxTU2fUG5DcWDDV\n"
+"hVZ9bZ9R94uD1HuG7IB7SQ==\n"
+"-----END ENCRYPTED PRIVATE KEY-----";
+    const size_t lenPrivKey = 3413;
+    FILE *privKeyFile = fopen(PRIVATE_KEY_FILENAME, "wb");
+    OFCHECK(privKeyFile);
+    OFCHECK(lenPrivKey == fwrite(privKey, 1, lenPrivKey, privKeyFile));
+    fclose(privKeyFile);
+
+    const char* pubSelfSIgnedCert =
+    "-----BEGIN CERTIFICATE-----\n"
+"MIIFpDCCA4ygAwIBAgIJAJRhU6soYQspMA0GCSqGSIb3DQEBCwUAMGcxCzAJBgNV\n"
+"BAYTAkRFMQ8wDQYDVQQIDAZEY21UbHMxDjAMBgNVBAcMBVRlc3RzMQ4wDAYDVQQK\n"
+"DAVPRkZJUzEOMAwGA1UECwwFRENNVEsxFzAVBgNVBAMMDmRpY29tQG9mZmlzLmRl\n"
+"MB4XDTE5MDIyNTE0MjY0NVoXDTI5MDIyNTE0MjY0NVowZzELMAkGA1UEBhMCREUx\n"
+"DzANBgNVBAgMBkRjbVRsczEOMAwGA1UEBwwFVGVzdHMxDjAMBgNVBAoMBU9GRklT\n"
+"MQ4wDAYDVQQLDAVEQ01USzEXMBUGA1UEAwwOZGljb21Ab2ZmaXMuZGUwggIiMA0G\n"
+"CSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQC+YYUnYLhLIuhizqUUO4KtzaKmqJ4z\n"
+"Y5mn9H9J0U721C932F702CX38KhZOMRc/7C0cNxdYWDFS7iEjl90kwNmfkdVK8Xj\n"
+"dLQ6GVTjvkVI6caeQBe3MgSvVRtczmhMqgP8DoNFSP7/OUTTcTcoHquoVIrViCOH\n"
+"8vc/6mfBFA5qsoGDwi3A/LgUh/mNHqAZqAkomEzmHihNrM9RA8a+7doqjNf7IrQU\n"
+"Hx7ubK+RozprXvqMTKGddy+gbbmFzCyWLgDC2ak25p1qMNVqDlZYhrfV+Q0M7fQG\n"
+"OJw97SLjyHXT9P93IWO+WbLCdSmj/GBIx/nLMzRSVUbPPvUm37uhy2mSfgIhE8w8\n"
+"ybVnXRLJdxUyHwpZVm+UktCPv/IU8LdgxA1sKx7+S/7BgwIS0rXX3O3yeB1z/dFS\n"
+"kT44Ju+Ze8MAPxVoyWbF+SaKmy9LcsRpjjIusJLTDT3W1Pw+AymYDt0BKq5rDnd4\n"
+"gx/dKuRd/921GFAnrZE86rmWbvTuqYGCYeaJfRnhCDmjWLgq/jlrc37fTv2TJXF7\n"
+"TGNjkfGsjS1StC9IOnGXyhV0klvK5xxPvIGVHUbVi2bXDW9HUTmtZ6O0vFM7NgRh\n"
+"UimndmrLbEJJGNGG36h5kIMe5xo7C99utu+d077itL4ZPcOyeeEHXaObjxQEzQ8x\n"
+"RnkDOWzIDTU9ZQIDAQABo1MwUTAdBgNVHQ4EFgQU84HK6/XZJXpkS53bNQSma5YR\n"
+"QIUwHwYDVR0jBBgwFoAU84HK6/XZJXpkS53bNQSma5YRQIUwDwYDVR0TAQH/BAUw\n"
+"AwEB/zANBgkqhkiG9w0BAQsFAAOCAgEAdNRVhkbUS77PlG6TvwYBhRwijy0F3rUX\n"
+"BVs4MidSaK8V9Cxa/m018GV0xoz52zIibLUiKLvRUNo3qS24Gbfbh9fdKoIBaTpG\n"
+"ike3lS19ddovqQE6WsTTQWjbVP5+B4BVvGbqJNBUFI1vn8dxHFCmWDWqQJy44PqF\n"
+"bp88vegFc51dTsrWVWfvTVUP56vmINm2EnvCHEJjQXp7AODlvanC358oJ18YWHzX\n"
+"WgGqTE7J4Eab9lmRWMb+ArHvVqwXm5aIFAl/JJ3faJIgW1pqGyKnlQYeiQOOy+YG\n"
+"pXCqUxiTMyWP27hoCMG5v3IXdbmIXedD6CwAV0yq6uZUz62g23rXaJiG0wILWMP0\n"
+"xzPGnBJHz7VmXMPX1Fs8AxgHZn41N1LCT1BmnFMPmTQb4v/eHSihYHVORkvhdwQu\n"
+"LJxKz8oawnka6n9UXF+rVdJjXCeYEA5Y9ThW6Qio3vjrFR5vX70EuVlu/bXqSg3J\n"
+"tw+7Gn0C1XfjBtnRJPcSKdBhrkooB2Kl6nkgxy1yTyOXvG1xLeJgJw6/MiCuFu5g\n"
+"DZRABWjQPrqv8rFyYm7jwa8sTAppmANazi6SsUGC27cXICVGw3zP7FrXI3jerMkv\n"
+"LN+tQ/fnbPFx0kM8PW8Fx6/ns51MMzDZkCdD8yM/Bg74culg20rr25MAa/L0VGq8\n"
+"x+yqEeQzzYQ=\n"
+"-----END CERTIFICATE-----";
+    const size_t lenPubSelfSignedCert = 2016;
+    FILE *pubSelfSignedCertFile = fopen(PUBLIC_SELFSIGNED_CERT_FILENAME, "wb");
+    OFCHECK(pubSelfSignedCertFile);
+    OFCHECK(lenPubSelfSignedCert == fwrite(pubSelfSIgnedCert, 1, lenPubSelfSignedCert, pubSelfSignedCertFile));
+    fclose(pubSelfSignedCertFile);
+}
+
+// Function for initialization of logs with console appender
+void initLogs()
+{
+    const char * const LOG_PATTERN_LAYOUT = "%D{%Y-%m-%d %H:%M:%S.%q} %5p: %m%n";
+    OFunique_ptr < dcmtk::log4cplus::Layout > layout(new dcmtk::log4cplus::PatternLayout(LOG_PATTERN_LAYOUT));
+    dcmtk::log4cplus::SharedAppenderPtr console(new dcmtk::log4cplus::ConsoleAppender(OFTrue /* logToStdErr */, OFTrue /* immediateFlush */));
+    console->setLayout(OFmove(layout));
+    dcmtk::log4cplus::Logger log = dcmtk::log4cplus::Logger::getRoot();
+    log.removeAllAppenders();
+    log.addAppender(console);
+    log.setLogLevel(OFLogger::DEBUG_LOG_LEVEL);
+}
+
+
+// Test case that checks server scp tls connection
+OFTEST_FLAGS(dcmtls_scp_tls, EF_None)
+{
+    /// Write key and cert files
+    write_temp_key_cert_files();
+
+    /// Init logs
+    initLogs();
+
+    /// Init scp tls layer
+    DcmTransportLayerStatus result;
+    DcmTLSTransportLayer scpTlsLayer(NET_ACCEPTOR, NULL, OFTrue);
+    scpTlsLayer.setPrivateKeyPasswd(PRIVATE_KEY_PWD);
+    result = scpTlsLayer.setPrivateKeyFile(PRIVATE_KEY_FILENAME, DCF_Filetype_PEM);
+    OFCHECK(result == TCS_ok);
+    result = scpTlsLayer.setCertificateFile(PUBLIC_SELFSIGNED_CERT_FILENAME, DCF_Filetype_PEM);
+    OFCHECK(result == TCS_ok);
+    OFCHECK(scpTlsLayer.checkPrivateKeyMatchesCertificate());
+    scpTlsLayer.setCertificateVerification(DCV_ignoreCertificate);
+
+    /// Init and run Scp server with tls
+    TestSCP scp;
+    DcmSCPConfig& config = scp.getConfig();
+    config.setPort(11112);
+    config.setAETitle("ACCEPTOR");
+    config.setACSETimeout(30);
+    config.setConnectionTimeout(1);
+    config.setMaxReceivePDULength(16856);
+    config.setHostLookupEnabled(false);
+    config.setConnectionBlockingMode(DUL_NOBLOCK);
+    config.setRespondWithCalledAETitle("REQUESTOR");
+    OFList<OFString> xfers;
+    xfers.push_back(UID_LittleEndianImplicitTransferSyntax);
+    OFCHECK(config.addPresentationContext(UID_VerificationSOPClass, xfers, ASC_SC_ROLE_SCP).good());
+
+    config.setTransportLayer(&scpTlsLayer);
+    scp.start();
+
+    // Ensure server is up and listening
+    force_sleep(1);
+
+    // Configure SCU and run it against SCP
+    DcmTLSSCU scu;
+    scu.setMaxReceivePDULength(16856);
+    scu.setDIMSEBlockingMode(DIMSE_NONBLOCKING);
+    scu.setDIMSETimeout(300);
+    scu.setACSETimeout(30);
+    scu.setPeerAETitle("ACCEPTOR");
+    scu.setAETitle("REQUESTOR");
+    scu.setPeerHostName("localhost");
+    scu.setPeerPort(11112);
+
+    scu.enableAuthentication(PRIVATE_KEY_FILENAME, PUBLIC_SELFSIGNED_CERT_FILENAME, PRIVATE_KEY_PWD, DCF_Filetype_PEM, DCF_Filetype_PEM);
+    scu.setPeerCertVerification(DCV_ignoreCertificate);
+
+    OFCHECK(scu.addPresentationContext(UID_VerificationSOPClass, xfers, ASC_SC_ROLE_SCU).good());
+
+    OFCHECK(scu.initNetwork().good());
+    OFCHECK(scu.negotiateAssociation().good());
+
+    scp.m_set_stop_after_assoc = OFTrue;
+    scp.m_set_stop_after_timeout = OFTrue;
+    if (scu.isConnected())
+        OFCHECK(scu.releaseAssociation().good());
+    scp.join();
+}
+
+
+// Test case that checks server scp tls connection
+OFTEST_FLAGS(dcmtls_scp_pool_tls, EF_None)
+{
+    /// Write key and cert files
+    write_temp_key_cert_files();
+
+    /// Init logs
+    initLogs();
+
+    /// Init scp tls layer
+    DcmTransportLayerStatus result;
+    DcmTLSTransportLayer scpTlsLayer(NET_ACCEPTOR, NULL, OFTrue);
+    scpTlsLayer.setPrivateKeyPasswd(PRIVATE_KEY_PWD);
+    result = scpTlsLayer.setPrivateKeyFile(PRIVATE_KEY_FILENAME, DCF_Filetype_PEM);
+    OFCHECK(result == TCS_ok);
+    result = scpTlsLayer.setCertificateFile(PUBLIC_SELFSIGNED_CERT_FILENAME, DCF_Filetype_PEM);
+    OFCHECK(result == TCS_ok);
+    OFCHECK(scpTlsLayer.checkPrivateKeyMatchesCertificate());
+    scpTlsLayer.setCertificateVerification(DCV_ignoreCertificate);
+
+    /// Init and run Scp server with tls
+    TestPool pool;
+    DcmSCPConfig& config = pool.getConfig();
+    config.setPort(11112);
+    config.setAETitle("ACCEPTOR");
+    config.setACSETimeout(30);
+    config.setConnectionTimeout(1);
+    config.setMaxReceivePDULength(16856);
+    config.setHostLookupEnabled(false);
+    config.setConnectionBlockingMode(DUL_NOBLOCK);
+    config.setRespondWithCalledAETitle("REQUESTOR");
+    OFList<OFString> xfers;
+    xfers.push_back(UID_LittleEndianImplicitTransferSyntax);
+    OFCHECK(config.addPresentationContext(UID_VerificationSOPClass, xfers, ASC_SC_ROLE_DEFAULT).good());
+    config.setTransportLayer(&scpTlsLayer);
+    pool.setMaxThreads(20);
+    pool.start();
+
+    // Ensure server is up and listening
+    force_sleep(1);
+
+    OFVector<TestTLSSCU*> scus(20);
+    OFVector<DcmTLSTransportLayer*> scuTlsLayers;
+    for (OFVector<TestTLSSCU*>::iterator it1 = scus.begin(); it1 != scus.end(); ++it1)
+    {
+        *it1 = new TestTLSSCU;
+        (*it1)->setMaxReceivePDULength(16856);
+        (*it1)->setDIMSEBlockingMode(DIMSE_NONBLOCKING);
+        (*it1)->setDIMSETimeout(300);
+        (*it1)->setACSETimeout(30);
+        (*it1)->setPeerAETitle("ACCEPTOR");
+        (*it1)->setAETitle("REQUESTOR");
+        (*it1)->setPeerHostName("localhost");
+        (*it1)->setPeerPort(11112);
+        (*it1)->enableAuthentication(PRIVATE_KEY_FILENAME, PUBLIC_SELFSIGNED_CERT_FILENAME, PRIVATE_KEY_PWD, DCF_Filetype_PEM, DCF_Filetype_PEM);
+        (*it1)->setPeerCertVerification(DCV_ignoreCertificate);
+
+        OFList<OFString> ts;
+        ts.push_back(UID_LittleEndianImplicitTransferSyntax);
+        OFCHECK((*it1)->addPresentationContext(UID_VerificationSOPClass, ts, ASC_SC_ROLE_SCU).good());
+        (*it1)->initNetwork();
+    }
+
+    // "ensure" the pool is initialized before any SCU starts connecting to it. The initialization
+    // can take a couple of seconds on older systems, e.g. debian i368.
+    force_sleep(5);
+
+    for (OFVector<TestTLSSCU*>::const_iterator it2 = scus.begin(); it2 != scus.end(); ++it2)
+    {
+        (*it2)->start();
+    }
+
+    for (OFVector<TestTLSSCU*>::iterator it3 = scus.begin(); it3 != scus.end(); ++it3)
+    {
+        (*it3)->join();
+        OFCHECK((*it3)->result.good());
+        delete *it3;
+    }
+
+    for (OFVector<DcmTLSTransportLayer*>::iterator it4 = scuTlsLayers.begin(); it4 != scuTlsLayers.end(); ++it4)
+    {
+        delete *it4;
+    }
+
+    pool.stopAfterCurrentAssociations();
+    pool.join();
+}
+
+#endif // WITH_OPENSSL
+
+#endif // WITH_THREADS
+
+#if (!defined(WITH_THREADS)) || (!defined(WITH_OPENSSL))
+
+// Dummy versions of the test cases. Needed to prevent ctest test failures.
+OFTEST(dcmtls_scp_tls)
+{
+}
+
+OFTEST(dcmtls_scp_pool_tls)
+{
+}
+
+// This dummy function creates a dependency on libdcmnet that is required when compiling
+// on NetBSD with libwrap support enabled and OpenSSL support disabled. Otherwise there
+// would be a linker error complaining about unresolved symbols allow_severity and deny_severity.
+
+DcmTransportLayer *tscuscptls_dummyFunction()
+{
+  return new DcmTransportLayer();
+}
+
+#endif
index 94cd429ad8980f72f746b12466b38ca555fab9e2..1497a24f1e85719e68ba7c61eeeacf114c033e69 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016-2018, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -47,7 +47,7 @@ public:
   {
     public:
 
-      // Allow read/write functions in DcmIODUtil to access class internals
+      /// Allow read/write functions in DcmIODUtil to access class internals
       friend class DcmIODUtil;
 
       /** Create TrcMeasurement::Values from minimal data.
@@ -111,7 +111,7 @@ public:
       Values();
   };
 
-   // Allow read/write functions in DcmIODUtil to access class internals
+   /// Allow read/write functions in DcmIODUtil to access class internals
    friend class DcmIODUtil;
 
   /** Create TrcMeasurement from minimal data
index 97a7110e86fb8ce98d356ce71fdbc7fb52cfe81b..b55b33d3e6e10a055426d80fee907f9fda6f647e 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -96,6 +96,7 @@ public:
   /** Return references to images that contributed to the Tractography Results
    *  object. The references is populated from the content of the Referenced
    *  Instance Sequence (and will be used for populating it when writing)
+   *  @return Reference to IODReferences
    */
   virtual IODReferences& getReferencedInstances();
 
index 98dab552810329c71b234a2504b6d2a59f0ed552..ecf47820ffda1d0e20f5400010c6833b79928629 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016-2017, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -45,7 +45,7 @@ class DCMTK_DCMTRACT_EXPORT TrcStatistic
 
 public:
 
-  // Allow read/write functions in DcmIODUtil to access class internals
+  /// Allow read/write functions in DcmIODUtil to access class internals
   friend class DcmIODUtil;
 
   /** Constructor
index a18409d06d39598b297dcba5d7772751a8269c2b..3b57cf12a0c5b76bad0812f3e02264ed5e8470ed 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -37,7 +37,7 @@ class DCMTK_DCMTRACT_EXPORT TrcTrack
 
 public:
 
-  // Allow read/write functions in DcmIODUtil to access class internals
+  /// Allow read/write functions in DcmIODUtil to access class internals
   friend class DcmIODUtil;
 
   /** Create TrcTrack object from required data
@@ -115,6 +115,7 @@ public:
   virtual size_t getTrackData(const Float32*& data) const;
 
   /** Get Number of data points
+   *  @return The number of data points
    */
   virtual size_t getNumDataPoints();
 
index d465e5f969c55bdb6de841d3c6789745c00c79aa..97bcf9d71202a7d22c053cb96aac24ebd58330ac 100644 (file)
@@ -1,6 +1,6 @@
     /*
  *
- *  Copyright (C) 2016-2018, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -47,7 +47,7 @@ class DCMTK_DCMTRACT_EXPORT TrcTrackSet
 
 public:
 
-  // Allow read/write functions in DcmIODUtil to access class internals
+  /// Allow read/write functions in DcmIODUtil to access class internals
   friend class DcmIODUtil;
 
   /** Create TrcTrackSet object by proving required data
@@ -314,6 +314,7 @@ public:
    *  @param  value The statistical value
    *  @param  statistic Returns the created statistic, if successful. NULL
    *          otherwise
+   *  @return EC_Normal if successful, error otherwise
    */
   virtual OFCondition addTrackSetStatistic(const CodeSequenceMacro& typeCode,
                                            const CodeSequenceMacro& typeModifierCode,
index 41c5806d6da817a5b1e3bf418483148b1f9cdd01..f341392d3ff4b7a9415f3c1588dd3b496f7d61a5 100644 (file)
@@ -9,15 +9,17 @@ trcmeasurement.o: trcmeasurement.cc \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -43,29 +45,26 @@ trcmeasurement.o: trcmeasurement.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../include/dcmtk/dcmtract/trcmeasurement.h \
  ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
@@ -126,7 +125,9 @@ trcmeasurement.o: trcmeasurement.cc \
 trcmodtractresults.o: trcmodtractresults.cc \
  ../../config/include/dcmtk/config/osconfig.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/oftypes.h \
  ../../ofstd/include/dcmtk/ofstd/ofdefine.h \
  ../../ofstd/include/dcmtk/ofstd/ofcast.h \
@@ -134,14 +135,13 @@ trcmodtractresults.o: trcmodtractresults.cc \
  ../../ofstd/include/dcmtk/ofstd/ofstdinc.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -167,29 +167,27 @@ trcmodtractresults.o: trcmodtractresults.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../include/dcmtk/dcmtract/trcmodtractresults.h \
  ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
@@ -262,15 +260,17 @@ trcstatistic.o: trcstatistic.cc \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -296,29 +296,26 @@ trcstatistic.o: trcstatistic.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../include/dcmtk/dcmtract/trcstatistic.h \
  ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
@@ -386,15 +383,17 @@ trctrack.o: trctrack.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -420,29 +419,26 @@ trctrack.o: trctrack.cc ../../config/include/dcmtk/config/osconfig.h \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../include/dcmtk/dcmtract/trctrack.h \
  ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
  ../include/dcmtk/dcmtract/trctypes.h \
@@ -462,14 +458,16 @@ trctrackset.o: trctrackset.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcuid.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -493,29 +491,26 @@ trctrackset.o: trctrackset.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../include/dcmtk/dcmtract/trctrackset.h \
  ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
@@ -587,15 +582,17 @@ trctractographyresults.o: trctractographyresults.cc \
  ../../ofstd/include/dcmtk/ofstd/ofstream.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdefine.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodutil.h \
- ../../ofstd/include/dcmtk/ofstd/oftraits.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
+ ../../ofstd/include/dcmtk/ofstd/offile.h \
  ../../ofstd/include/dcmtk/ofstd/ofstring.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
- ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
- ../../ofstd/include/dcmtk/ofstd/ofthread.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../ofstd/include/dcmtk/ofstd/ofstd.h \
+ ../../ofstd/include/dcmtk/ofstd/oflist.h \
+ ../../ofstd/include/dcmtk/ofstd/oftraits.h \
  ../../ofstd/include/dcmtk/ofstd/ofcond.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
+ ../../ofstd/include/dcmtk/ofstd/oflimits.h \
+ ../../config/include/dcmtk/config/arith.h \
+ ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctypes.h \
  ../../oflog/include/dcmtk/oflog/oflog.h \
  ../../oflog/include/dcmtk/oflog/logger.h \
@@ -621,29 +618,26 @@ trctractographyresults.o: trctractographyresults.cc \
  ../../oflog/include/dcmtk/oflog/logmacro.h \
  ../../oflog/include/dcmtk/oflog/helpers/snprintf.h \
  ../../oflog/include/dcmtk/oflog/tracelog.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcobject.h \
+ ../../ofstd/include/dcmtk/ofstd/ofglobal.h \
+ ../../ofstd/include/dcmtk/ofstd/ofthread.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcerror.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcxfer.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvr.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctag.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctagkey.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcstack.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
- ../../ofstd/include/dcmtk/ofstd/offile.h \
- ../../ofstd/include/dcmtk/ofstd/ofstd.h \
- ../../ofstd/include/dcmtk/ofstd/oflist.h \
- ../../ofstd/include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../../ofstd/include/dcmtk/ofstd/oferror.h \
  ../../dcmdata/include/dcmtk/dcmdata/dclist.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcdatset.h \
- ../../dcmdata/include/dcmtk/dcmdata/dcitem.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcpcache.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcdatutl.h \
- ../../ofstd/include/dcmtk/ofstd/ofdate.h \
- ../../ofstd/include/dcmtk/ofstd/oftime.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcelem.h \
+ ../../dcmdata/include/dcmtk/dcmdata/dcsequen.h \
  ../../dcmiod/include/dcmtk/dcmiod/ioddef.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodrules.h \
- ../../ofstd/include/dcmtk/ofstd/ofmap.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodtypes.h \
- ../../dcmiod/include/dcmtk/dcmiod/cielabutil.h \
+ ../../ofstd/include/dcmtk/ofstd/ofmap.h \
+ ../../ofstd/include/dcmtk/ofstd/ofdate.h \
+ ../../ofstd/include/dcmtk/ofstd/oftime.h \
  ../../dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h \
  ../../dcmdata/include/dcmtk/dcmdata/dctk.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcswap.h \
@@ -698,19 +692,19 @@ trctractographyresults.o: trctractographyresults.cc \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrol.h \
  ../../dcmdata/include/dcmtk/dcmdata/dcvrov.h \
  ../../dcmdata/include/dcmtk/dcmdata/cmdlnarg.h \
- ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodmacro.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modbase.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodreferences.h \
  ../include/dcmtk/dcmtract/trctractographyresults.h \
  ../../dcmiod/include/dcmtk/dcmiod/iodcommn.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
+ ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
  ../../dcmiod/include/dcmtk/dcmiod/modpatient.h \
  ../../dcmiod/include/dcmtk/dcmiod/modpatientstudy.h \
  ../../ofstd/include/dcmtk/ofstd/ofoption.h \
  ../../ofstd/include/dcmtk/ofstd/ofalign.h \
- ../../dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h \
- ../../dcmiod/include/dcmtk/dcmiod/modequipment.h \
- ../../dcmiod/include/dcmtk/dcmiod/modgeneralseries.h \
- ../../dcmiod/include/dcmtk/dcmiod/modfor.h \
  ../../dcmiod/include/dcmtk/dcmiod/modsopcommon.h \
  ../../dcmiod/include/dcmtk/dcmiod/modenhequipment.h \
  ../include/dcmtk/dcmtract/trctypes.h ../include/dcmtk/dcmtract/trcdef.h \
index 3bf3662c01b722a646026670c667d1992d1b5198..f7aac1d7749021380a247c2de4a88cfdf736c400 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2016-2018, Open Connections GmbH
+ *  Copyright (C) 2016-2019, Open Connections GmbH
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation are maintained by
@@ -73,6 +73,7 @@ void TrcTrack::resetRules()
 
 OFCondition TrcTrack::check(const OFBool quiet)
 {
+  OFCondition result;
   // Report errors but ignore them
   IODComponent::check(quiet);
   const Float32* data = NULL;
@@ -84,27 +85,26 @@ OFCondition TrcTrack::check(const OFBool quiet)
     {
       if (count % 3 == 0)
       {
-        return EC_Normal;
+        result = EC_Normal;
       }
       else
       {
         DCMTRACT_ERROR("Point Coordinates Data must have x,y,z coordinates for every point but has length: " << count);
-        return IOD_EC_InvalidElementValue;
+        result = IOD_EC_InvalidElementValue;
       }
     }
     else
     {
       DCMTRACT_ERROR("Point Coordinates Data empty");
-      return IOD_EC_InvalidElementValue;
+      result = IOD_EC_InvalidElementValue;
     }
   }
   else
   {
     DCMTRACT_ERROR("Point Coordinates Data element missing");
-    return IOD_EC_MissingAttribute;
+    result = IOD_EC_MissingAttribute;
   }
-  // should never get here
-  return EC_Normal;
+  return result;
 }
 
 
@@ -278,6 +278,7 @@ OFCondition TrcTrack::setTrackData(const Float32* trackDataPoints,
 OFCondition TrcTrack::setRecommendedDisplayCIELabValues(const Uint16* colors,
                                                         const size_t numColors)
 {
+  OFCondition result;
   if ( (numColors == 0) && (colors == NULL))
   {
     m_Item->findAndDeleteElement(DCM_RecommendedDisplayCIELabValue);
@@ -296,8 +297,6 @@ OFCondition TrcTrack::setRecommendedDisplayCIELabValues(const Uint16* colors,
   {
     return m_Item->putAndInsertUint16Array(DCM_RecommendedDisplayCIELabValueList, colors, OFstatic_cast(unsigned long, numColors * 3));
   }
-  // should never get here
-  return TRC_EC_InvalidColorInformation;
 }
 
 
index 44d496b3a433ad6c89e3f6917a345191a4e83110..71d8f57b70c22621d09176a273ffe8847ce859e6 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1996-2019, OFFIS e.V.
+ *  Copyright (C) 1996-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -133,9 +133,6 @@ WlmConsoleEngineFileSystem::WlmConsoleEngineFileSystem( int argc, char *argv[],
       cmd->addOption("--keep-char-set",       "-csk",    "return character set provided in file");
     cmd->addSubGroup("other processing options:");
       cmd->addOption("--no-sq-expansion",     "-nse",    "disable expansion of empty sequences in C-FIND\nrequest messages");
-      cmd->addOption("--request-file-path",   "-rfp", 1, "[p]ath: string", "path to store request files to");
-      cmd->addOption("--request-file-format", "-rff", 1, "[f]ormat: string (default: #t.dump)", "request file name format");
-
 
   cmd->addGroup("network options:");
     cmd->addSubGroup("preferred network transfer syntaxes:");
@@ -192,6 +189,11 @@ WlmConsoleEngineFileSystem::WlmConsoleEngineFileSystem( int argc, char *argv[],
       cmd->addOption("--max-pdu",             "-pdu", 1, opt4.c_str(), opt3.c_str());
       cmd->addOption("--disable-host-lookup", "-dhl",    "disable hostname lookup");
 
+  cmd->addGroup("output options:");
+    cmd->addSubGroup("general:");
+      cmd->addOption("--request-file-path",   "-rfp", 1, "[p]ath: string", "path to store request files to");
+      cmd->addOption("--request-file-format", "-rff", 1, "[f]ormat: string (default: #t.dump)", "request file name format");
+
   // Evaluate command line.
   prepareCmdLineArgs( argc, argv, applicationName );
   if( app->parseCommandLine( *cmd, argc, argv ) )
@@ -223,6 +225,7 @@ WlmConsoleEngineFileSystem::WlmConsoleEngineFileSystem( int argc, char *argv[],
 
     OFLog::configureFromCommandLine(*cmd, *app);
 
+    // general options
 #if defined(HAVE_FORK) || defined(_WIN32)
     cmd->beginOptionBlock();
     if (cmd->findOption("--single-process")) opt_singleProcess = OFTrue;
@@ -233,19 +236,15 @@ WlmConsoleEngineFileSystem::WlmConsoleEngineFileSystem( int argc, char *argv[],
 #endif
 #endif
 
+    // input options
     if( cmd->findOption("--data-files-path") ) app->checkValue(cmd->getValue(opt_dfPath));
-    if( cmd->findOption("--request-file-path") ) app->checkValue(cmd->getValue(opt_rfPath));
-    if( cmd->findOption("--request-file-format") )
-    {
-        app->checkDependence("--request-file-format", "--request-file-path", !opt_rfPath.empty());
-        app->checkValue(cmd->getValue(opt_rfFormat));
-    }
 
     cmd->beginOptionBlock();
     if( cmd->findOption("--enable-file-reject") ) opt_enableRejectionOfIncompleteWlFiles = OFTrue;
     if( cmd->findOption("--disable-file-reject") ) opt_enableRejectionOfIncompleteWlFiles = OFFalse;
     cmd->endOptionBlock();
 
+    // processing options
     cmd->beginOptionBlock();
     if( cmd->findOption("--return-no-char-set") ) opt_returnedCharacterSet = RETURN_NO_CHARACTER_SET;
     if( cmd->findOption("--return-iso-ir-100") ) opt_returnedCharacterSet = RETURN_CHARACTER_SET_ISO_IR_100;
@@ -254,6 +253,7 @@ WlmConsoleEngineFileSystem::WlmConsoleEngineFileSystem( int argc, char *argv[],
 
     if( cmd->findOption("--no-sq-expansion") ) opt_noSequenceExpansion = OFTrue;
 
+    // network options
     cmd->beginOptionBlock();
     if( cmd->findOption("--prefer-uncompr") ) opt_networkTransferSyntax = EXS_Unknown;
     if( cmd->findOption("--prefer-little") ) opt_networkTransferSyntax = EXS_LittleEndianExplicit;
@@ -316,6 +316,14 @@ WlmConsoleEngineFileSystem::WlmConsoleEngineFileSystem( int argc, char *argv[],
     if( cmd->findOption("--sleep-during") ) app->checkValue(cmd->getValueAndCheckMin(opt_sleepDuringFind, 0));
     if( cmd->findOption("--max-pdu") ) app->checkValue(cmd->getValueAndCheckMinMax(opt_maxPDU, ASC_MINIMUMPDUSIZE, ASC_MAXIMUMPDUSIZE));
     if( cmd->findOption("--disable-host-lookup") ) dcmDisableGethostbyaddr.set(OFTrue);
+
+    // output options
+    if( cmd->findOption("--request-file-path") ) app->checkValue(cmd->getValue(opt_rfPath));
+    if( cmd->findOption("--request-file-format") )
+    {
+        app->checkDependence("--request-file-format", "--request-file-path", !opt_rfPath.empty());
+        app->checkValue(cmd->getValue(opt_rfFormat));
+    }
   }
 
   // dump application information
index f096db7bb38b805ff9d1fdd79ea1dd11396d1e34..652b214e0705343479ae0eabfcaf53b6b3a5a9be 100644 (file)
@@ -104,12 +104,6 @@ other processing options:
   -nse  --no-sq-expansion
           disable expansion of empty sequences in C-FIND
           request messages
-
-  -rfp  --request-file-path  [p]ath: string
-          path to store request files to
-
-  -rff  --request-file-format  [f]ormat: string (default: #t.dump)
-          request file name format
 \endverbatim
 
 \subsection wlmscpfs_network_options network options
@@ -188,6 +182,17 @@ other network options:
           disable hostname lookup
 \endverbatim
 
+\subsection wlmscp_output_options output options
+\verbatim
+general:
+
+  -rfp  --request-file-path  [p]ath: string
+          path to store request files to
+
+  -rff  --request-file-format  [f]ormat: string (default: #t.dump)
+          request file name format
+\endverbatim
+
 \section wlmscpfs_notes NOTES
 
 The semantic impacts of the above mentioned options is clear for the majority
@@ -508,6 +513,6 @@ It is an error if no data dictionary can be loaded.
 
 \section wlmscpfs_copyright COPYRIGHT
 
-Copyright (C) 1996-2019 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
+Copyright (C) 1996-2020 by OFFIS e.V., Escherweg 2, 26121 Oldenburg, Germany.
 
 */
index a2f28f16fafb339af3eb693d613fe5fca6cc573a..1efb34e69f67c8625365ec2953e67705aa933bc2 100644 (file)
@@ -665,11 +665,11 @@ OFBool WlmDataSourceFileSystem::SetReadlock()
   // assign path to a local variable
   OFString lockname = dfPath;
 
-  // if the given path does not show a PATH_SEPERATOR at the end, append one
+  // if the given path does not show a PATH_SEPARATOR at the end, append one
   if( !lockname.empty() && lockname[lockname.length()-1] != PATH_SEPARATOR )
     lockname += PATH_SEPARATOR;
 
-  // append calledApplicationEntityTitle, another PATH_SEPERATOR,
+  // append calledApplicationEntityTitle, another PATH_SEPARATOR,
   // and LOCKFILENAME to the given path (and separator)
   lockname += calledApplicationEntityTitle;
   lockname += PATH_SEPARATOR;
index 5ce8f9c8da502625e4287c7f46a3dd4d5f60116a..f2ae1c0223e08e8aaf55bee3672f3cbc1b6e7b3d 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1996-2018, OFFIS e.V.
+ *  Copyright (C) 1996-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -671,8 +671,8 @@ OFBool WlmFileSystemInteractionManager::IsUniversalMatch( DcmSequenceOfItems& qu
       {
         const OFPair<DcmTagKey,OFBool>& key = *it;
 #endif
-        DcmElement* query = OFnullptr;
-        if( pQueryItem->findAndGetElement( key.first, query, OFFalse ).good() && query && !query->isUniversalMatch( normalize, normalizeWildCards && key.second ) )
+        DcmElement* query_elem = OFnullptr;
+        if( pQueryItem->findAndGetElement( key.first, query_elem, OFFalse ).good() && query_elem && !query_elem->isUniversalMatch( normalize, normalizeWildCards && key.second ) )
           return OFFalse;
       }
 
@@ -685,10 +685,10 @@ OFBool WlmFileSystemInteractionManager::IsUniversalMatch( DcmSequenceOfItems& qu
       {
         const OFPair<DcmTagKey,DcmTagKey>& combinedKey = *it;
 #endif
-        DcmElement* query = OFnullptr;
-        if( pQueryItem->findAndGetElement( combinedKey.first, query, OFFalse ).good() && query && !query->isUniversalMatch( normalize, normalizeWildCards ) )
+        DcmElement* query_elem = OFnullptr;
+        if( pQueryItem->findAndGetElement( combinedKey.first, query_elem, OFFalse ).good() && query_elem && !query_elem->isUniversalMatch( normalize, normalizeWildCards ) )
           return OFFalse;
-        else if( pQueryItem->findAndGetElement( combinedKey.second, query, OFFalse ).good() && query && !query->isUniversalMatch( normalize, normalizeWildCards ) )
+        else if( pQueryItem->findAndGetElement( combinedKey.second, query_elem, OFFalse ).good() && query_elem && !query_elem->isUniversalMatch( normalize, normalizeWildCards ) )
           return OFFalse;
       }
 
@@ -702,8 +702,8 @@ OFBool WlmFileSystemInteractionManager::IsUniversalMatch( DcmSequenceOfItems& qu
       {
         const OFPair<DcmTagKey,MatchingKeys>& sequenceKey = *it;
 #endif
-        DcmElement* query = OFnullptr;
-        if( pQueryItem->findAndGetElement( sequenceKey.first, query, OFFalse ).good() && query && query->ident() == EVR_SQ && !IsUniversalMatch( OFstatic_cast( DcmSequenceOfItems&, *query ), sequenceKey.second, normalize, normalizeWildCards ) )
+        DcmElement* query_elem = OFnullptr;
+        if( pQueryItem->findAndGetElement( sequenceKey.first, query_elem, OFFalse ).good() && query_elem && query_elem->ident() == EVR_SQ && !IsUniversalMatch( OFstatic_cast( DcmSequenceOfItems&, *query_elem ), sequenceKey.second, normalize, normalizeWildCards ) )
           return OFFalse;
       }
   }
index 4d2f10bb02f79e091da7c8a5f5056d07b5cd36f4..6596cd8f1af33c6bc3b09069b5c7426c4831c804 100644 (file)
@@ -910,7 +910,7 @@ void WlmActivityManager::RemoveProcessFromTable( int pid )
     // if process can be found, delete it from list and free memory
     if ( ps->processId == pid )
     {
-      processTable.remove(*it);
+      processTable.erase(it);
       delete ps;
       return;
     }
diff --git a/docs/ANNOUNCE.365 b/docs/ANNOUNCE.365
new file mode 100644 (file)
index 0000000..f4d40ab
--- /dev/null
@@ -0,0 +1,169 @@
+ANNOUNCEMENT
+
+Version 3.6.5 of the OFFIS DCMTK (DICOM ToolKit) software is now available for
+public release.  This is a minor release that includes the following changes
+over the previous version 3.6.4:
+
+- DCMTK 3.6.5 builds correctly on older and up-to-date versions of GNU gcc
+  (4.4.7 to 9.2.0), Clang (3.4.2 to 9.0.0), AppleClang (11.0.0), Microsoft
+  Visual Studio (2008 to 2019), SunPro CC (5.14 and 5.15) and IBM XL C/C++
+  (16.1.1.3).
+
+- Tested with the following operating systems/environments:
+
+  - Android on arm64
+  - Cygwin on x86_64
+  - FreeBSD on x86_64
+  - Linux on x86_64 and x86
+  - MacOS X on x86_64
+  - NetBSD on x86_64
+  - OpenBSD on x86_64
+  - OpenIndiana on x86
+  - Solaris on x86
+  - Windows (and MinGW) on x86_64 and x86
+
+  For a complete list of tested systems and compilers, see the INSTALL file.
+
+- GNU Autoconf is still deprecated, running 'configure' emits a warning by
+  default.  Support for GNU Autoconf will be removed after this release.
+
+- Updated data dictionary, SOP Class, Frame of Reference and Transfer Syntax
+  UIDs for the recently approved changes to the DICOM standard (i.e. Supplements
+  and CPs), up to DICOM standard release DICOM 2019c plus Supplement 175 (Second
+  Generation Radiotherapy - C-Arm RT Treatment Modalities).
+
+- Added support for directory record "RADIOTHERAPY" that has been introduced
+  with Supplement 147 (Second Generation Radiotherapy - Prescription and Segment
+  Annotation).
+
+- Added support for the three new 64-bit integer VRs introduced with CP-1819:
+  Other 64-bit Very Long (OV), Signed 64-bit Very Long (SV) and Unsigned 64-bit
+  Very Long (UV).
+
+- Implemented support for the Extended BCP 195 TLS Profile, introduced with
+  Supplement 206, in the dcmtls module and the various TLS-enabled DCMTK tools.
+
+- Added option to "storescu" to rename files after processing them by appending
+  ".bad" or ".good" at the end of the filename.
+
+- Added new options to "wlmscpfs" that allow for dumping incoming C-FIND
+  requests to text files using a configurable directory and filename.
+
+- Updated automatically generated Context Group classes in "dcmsr"
+  (Structured Reporting) based on DICOM 2019c.  Also updated the Code
+  definitions from the supported coding schemes such as DICOM, NCIt and UMLS.
+
+- Further enhanced DICOM Structured Reporting (SR) module "dcmsr":
+
+  - Added support for the Performed Imaging Agent Administration SR IOD and the
+    Planned Imaging Agent Administration SR IOD introduced with Supplement 164.
+
+  - Added support for the Synchronization Module, which is required for some SR
+    IODs, e.g. Procedure Log SR or Performed Imaging Agent Administration SR.
+
+  - Added initial support for coding scheme "SCT" (SNOMED CT) by defining those
+    CODE_SCT_xxx code constants that are needed for the "cmr" submodule.
+
+  - Updated SR Template classes from DCMR for the 2019b edition of the DICOM
+    standard, i.e. all SRT (SNOMED RT) codes were replaced by their associated
+    SCT (SNOMED CT) counterparts. This change was introduced with CP-1850.
+
+  - Added new print flag PF_printEmptyCodes, which prints the text "empty code"
+    for empty codes instead of "invalid code". This new flag is e.g. used for
+    the output stream operator of the DSRCodedEntryValue class.
+
+- The list of elliptic curves to be negotiated as part of a TLS is now created
+  dynamically, i.e. it is tested at runtime which elliptic curves are supported
+  by the installed OpenSSL library.
+
+- Allow disabling Functional Group checks when writing Segmentations and
+  Parametric Map objects in order to speed up writing objects with many frames.
+
+- Added macro that enables the wide char (wchar_t*) support of the XML parser
+  that is part of the DCMTK (ofstd/ofxml). This support is limited to Windows
+  systems and still regarded as experimental (see documentation for details).
+
+- The tool "findscu" now always returns with a non-zero exit code when an error
+  occurred, e.g. when association negotiation failed.
+
+- CMake-related enhancements:
+
+  - DCMTK now understands and makes use of the CMake variable CMAKE_CXX_STANDARD
+    when a CMake version that supports it is employed (CMake 3.1.3 and newer).
+
+  - Added CMake option that controls whether DCMTK gets compiled using the
+    multi-threaded static or DLL runtime library when using MSVC on Windows.
+
+- Various fixes and extensions to the JPEG-LS implementation:
+
+  - Added command line options controlling how odd-length bitstreams are
+    padded to even length (for compatibility with HP LOCO).
+
+  - Added command line option that causes the decoder to store images even
+    though an error occurred during the decoding process, which may be helpful
+    for slightly truncated bitstreams.
+
+  - Enable setting of individual JPEG-LS encoding parameters
+    T1, T2, T3 and RESET.
+
+  - Various bugfixes in JPEG-LS encoder and decoder.
+
+- Fixed binary Segmentation object creation when width is not dividable by 8.
+
+- Fixed wrong DIMSE status codes A8xx (for C-STORE and C-FIND) and A800 (for
+  C-GET and C-MOVE), which were never defined in the official DICOM standard.
+  Now, the DCMTK uses the correct DIMSE status code 0122H for "SOP Class not
+  supported" for all DIMSE messages.
+
+- Fixed various issues that occurred after the official 3.6.4 release.
+  See CHANGES file for details.
+
+
+Many people have contributed to this new release of DCMTK, appearing here in
+alphabetical order.  Thank you very much for your support!
+
+  Victor Derks <vderks@delftdi.com>
+  Chinna Durai <chinnadurai410@gmail.com>
+  Holger Franke <franke@image-instruments.de>
+  Sergei Gordey <serg.gordey@gmail.com>
+  Daniel Grieger <Daniel.Grieger@ith-icoserve.com>
+  Bengt Gustafsson <Bengt.Gustafsson@contextvision.se>
+  Alexander Haderer <alexander.haderer@loescap.de>
+  Peter Klotz <Peter.Klotz@ith-icoserve.com>
+  Brian Lucas <brian.lucas@heartit.com>
+  Mathieu Malaterre <mathieu.malaterre@gmail.com>
+  Hans Meine <hans.meine@mevis.fraunhofer.de>
+  Maria Samoylova <mashanedyak@gmail.com>
+  Martin Wenger <Martin.Wenger@klinikum-hef.de>
+  Brian Wise <brian.wise@medtronic.com>
+  Grischa Zengel <ggz@zmt.info>
+
+  Andreas Gravgaard Andersen (GitHub user "agravgaard")
+  Hans Johnson (GitHub user "hjmjohnson")
+  Stefano Magni
+
+  Forum user "AlexanderLysenko"
+  GitHub user "eborisch"
+  GitHub user "FreddyFunk"
+
+Members of the DCMTK Team who have worked on this release are
+(in alphabetical order):
+
+  Pedro Arizpe Gomez <arizpegomez@offis.de>
+  Marco Eichelberg <eichelberg@offis.de>
+  Michael Onken <onken@open-connections.de>
+  Joerg Riesmeier <dicom@jriesmeier.com>
+  Jan Schlamelcher <schlamelcher@offis.de>
+
+Student associates:
+
+  Nikolas Goldhammer <nikolasgoldhammer@gmail.com>
+
+Also see CREDITS file for projects and companies who have been generously
+supporting DCMTK.
+
+The DCMTK software can be downloaded via:
+
+  https://dicom.offis.de/dcmtk or https://www.dcmtk.org/
+
+OFFIS e.V., Oldenburg, Germany, 2019-10-28
index 080382fcc86861e8050c2a950c52ad6326fc412b..0ffa83c18be8f8ba6417a40d77e6407a3f35bafc 100644 (file)
@@ -387,7 +387,7 @@ Release 3.2 (Public Release - 1997.06.02)
 
 - Added improved error/warning messages and backup of existing DICOMDIR
   file (the backup file has the suffix .BAK and is removed if the new
-  DICOMDIR file is sucessfully created).
+  DICOMDIR file is successfully created).
   Affects: dcmdata/apps/dcmgpdir.cc
 
 - Fixed bug related to renaming of temporary files accross file system
index 9e586e92f321a58e24d333c4e1237a63161794c4..6d6df583c1fea585f32ed93cf7bc94edf975e030 100644 (file)
@@ -1971,7 +1971,7 @@ Release 3.4.2 (Public Release - 2000-12-20)
            dcmnet/libsrc/dimdump.cc
            dcmnet/libsrc/dimse.cc
 
-- added optional paramter to DIMSE_storeUser that enables precise file size
+- added optional parameter to DIMSE_storeUser that enables precise file size
   information inside the store user callback.
   Thanks to Mohamed Ahmed Abd Elkader <mokader@iti-idsc.gov.eg>
   for the bug report.
index 88888fc486dcf1597ae7c7cb607f39d08deecc34..9f1d583c75ddcfdc2069c49d061b00e53a3919bc 100644 (file)
@@ -194,7 +194,7 @@ Release 3.5.0 (Public Release - 2001-06-14)
            dcmdata/libsrc/dcuid.cc
            dcmdata/libsrc/dicom.dic
 
-- Fixed memory leak that occured when parsing of a sequence failed.
+- Fixed memory leak that occurred when parsing of a sequence failed.
   Thanks to Harald Breitner <hbreitner@hectec.de> for the bug report and fix.
   Affects: dcmdata/libsrc/dcsequen.cc
 
index 870eeea756fc4dfe937ff94ba3b52eea1d7dade3..8c64260053a98bf7d3b143b8ceb13d04d93c8161 100644 (file)
@@ -2421,7 +2421,7 @@ Release 3.5.2 (Public Release - 2002-12-23)
 - Added vitual destructor to class OFStackLink
   Affects: ofstd/include/ofstack.h
 
-- Fixed memory leak that occured when compression of an image failed in
+- Fixed memory leak that occurred when compression of an image failed in
   a compression codec.
   Affects: dcmdata/libsrc/dcpixel.cc
 
index d3b35f171ed16bc27073aec27a892bc9b393baac..93511a4471fa9d0bf21f15e25d79f369d04b7152 100644 (file)
@@ -3499,7 +3499,7 @@ Release 3.6.0 (Public Release - 2011-01-06)
   Affects: dcmdata/libsrc/dcitem.cc
 
 - Fixed memory leak in assignment operators of DcmItem and DcmSequenceOfItems.
-  Replaced all code occurences of cleaning all elements from internal lists to
+  Replaced all code occurrences of cleaning all elements from internal lists to
   newly introduced function in DcmList.
   Affects: dcmdata/libsrc/dcitem.cc
            dcmdata/libsrc/dcsequen.cc
@@ -9311,7 +9311,7 @@ Release 3.6.0 (Public Release - 2011-01-06)
   Affects: dcmdata/libsrc/private.dic
 
 - Fixed memory leak in DIMSE_receiveDataSetInMemory when parameter dataObject
-  was passed as NULL and an error condition occured.
+  was passed as NULL and an error condition occurred.
   Thanks to Michael Doppler <m.doppler@gmail.com> for the report and fix.
   Affects: dcmnet/libsrc/dimse.cc
 
index 5d00a1e2a5df687a07f4ea7e89cb31c5d99ce732..658707b49d6e49d276d90c6966265a87362c03e0 100644 (file)
@@ -12024,7 +12024,7 @@ Release 3.6.2 (Public Release - 2017-07-14)
            dcmsr/tests/tsrdoctr.cc
            dcmsr/tests/tsrtree.cc
 
-- Avoid seperator if time component is empty:
+- Avoid separator if time component is empty:
   Avoid separator between date and time component of a "DateTime" value if the
   latter is empty. Before, there was a trailing space in the resulting string.
   Affects: dcmdata/include/dcmtk/dcmdata/dcvrdt.h
@@ -19120,7 +19120,7 @@ Release 3.6.2 (Public Release - 2017-07-14)
 **** Changes from 2013.01.04 (onken)
 
 - Made DcmAssociationConfiguration and underlying classes copy-constructable.
-  Replaced all occurences of DcmSimpleMap with OFMap.
+  Replaced all occurrences of DcmSimpleMap with OFMap.
   Affects: dcmnet/apps/Makefile.dep
            dcmnet/include/dcmtk/dcmnet/dcasccfg.h
            dcmnet/include/dcmtk/dcmnet/dccfenmp.h
index f7ef368f006d0bef724085fd321b014bc3b36159..5fb5e64ae781633cb49f4ba219fef414b51b472b 100644 (file)
@@ -482,7 +482,7 @@ Release 3.6.3 (Public Minor Release - 2018-02-05)
   Affects: dcmdata/libsrc/dcvrof.cc
 
 - Fixed buffer overrrun in DcmOtherFloat::writeXML():
-  Fixed buffer overrun in DcmOtherFloat::writeXML() that occured if
+  Fixed buffer overrun in DcmOtherFloat::writeXML() that occurred if
   an invalid element with VR=OF and Length=2 is present in the dataset
   that is converted to XML.
   Thanks to Gwan Yeong Kim for the bug report.
diff --git a/docs/CHANGES.366 b/docs/CHANGES.366
new file mode 100644 (file)
index 0000000..f3f46c9
--- /dev/null
@@ -0,0 +1,2782 @@
+
+Release 3.6.6 (Public Minor Release - 2021-01-14)
+
+**** Changes from 2021.01.14 (onken)
+
+- Updated release date in INSTALL file and for autoconf.
+  Affects: INSTALL
+           public/config/configure
+           public/config/configure.in
+
+- Final changes for Release 3.6.6.
+  Affects: ANNOUNCE
+           CMake/dcmtkPrepare.cmake
+           CREDITS
+           docs/CHANGES.366
+           doxygen/manpages/man1/cda2dcm.1
+           doxygen/manpages/man1/dcm2json.1
+           doxygen/manpages/man1/dcm2pdf.1
+           doxygen/manpages/man1/dcm2pnm.1
+           doxygen/manpages/man1/dcm2xml.1
+           doxygen/manpages/man1/dcmcjpeg.1
+           doxygen/manpages/man1/dcmcjpls.1
+           doxygen/manpages/man1/dcmconv.1
+           doxygen/manpages/man1/dcmcrle.1
+           doxygen/manpages/man1/dcmdjpeg.1
+           doxygen/manpages/man1/dcmdjpls.1
+           doxygen/manpages/man1/dcmdrle.1
+           doxygen/manpages/man1/dcmdspfn.1
+           doxygen/manpages/man1/dcmdump.1
+           doxygen/manpages/man1/dcmftest.1
+           doxygen/manpages/man1/dcmgpdir.1
+           doxygen/manpages/man1/dcmicmp.1
+           doxygen/manpages/man1/dcmj2pnm.1
+           doxygen/manpages/man1/dcml2pnm.1
+           doxygen/manpages/man1/dcmmkcrv.1
+           doxygen/manpages/man1/dcmmkdir.1
+           doxygen/manpages/man1/dcmmklut.1
+           doxygen/manpages/man1/dcmodify.1
+           doxygen/manpages/man1/dcmp2pgm.1
+           doxygen/manpages/man1/dcmprscp.1
+           doxygen/manpages/man1/dcmprscu.1
+           doxygen/manpages/man1/dcmpschk.1
+           doxygen/manpages/man1/dcmpsmk.1
+           doxygen/manpages/man1/dcmpsprt.1
+           doxygen/manpages/man1/dcmpsrcv.1
+           doxygen/manpages/man1/dcmpssnd.1
+           doxygen/manpages/man1/dcmqridx.1
+           doxygen/manpages/man1/dcmqrscp.1
+           doxygen/manpages/man1/dcmqrti.1
+           doxygen/manpages/man1/dcmquant.1
+           doxygen/manpages/man1/dcmrecv.1
+           doxygen/manpages/man1/dcmscale.1
+           doxygen/manpages/man1/dcmsend.1
+           doxygen/manpages/man1/dcmsign.1
+           doxygen/manpages/man1/dcod2lum.1
+           doxygen/manpages/man1/dconvlum.1
+           doxygen/manpages/man1/drtdump.1
+           doxygen/manpages/man1/dsr2html.1
+           doxygen/manpages/man1/dsr2xml.1
+           doxygen/manpages/man1/dsrdump.1
+           doxygen/manpages/man1/dump2dcm.1
+           doxygen/manpages/man1/echoscu.1
+           doxygen/manpages/man1/findscu.1
+           doxygen/manpages/man1/getscu.1
+           doxygen/manpages/man1/img2dcm.1
+           doxygen/manpages/man1/movescu.1
+           doxygen/manpages/man1/pdf2dcm.1
+           doxygen/manpages/man1/stl2dcm.1
+           doxygen/manpages/man1/storescp.1
+           doxygen/manpages/man1/storescu.1
+           doxygen/manpages/man1/termscu.1
+           doxygen/manpages/man1/wlmscpfs.1
+           doxygen/manpages/man1/xml2dcm.1
+           doxygen/manpages/man1/xml2dsr.1
+
+
+**** Changes from 2021.01.07 (onken)
+
+- Updated ANNOUNCE for Release 3.6.6
+  Affects: ANNOUNCE
+
+- Prepared source tree for DCMTK release 3.6.6.
+  Affects: ANNOUNCE
+           CMake/dcmtkPrepare.cmake
+           COPYRIGHT
+           CREDITS
+           INSTALL
+           VERSION
+           config/configure
+           config/configure.in
+           docs/CHANGES.366
+           doxygen/manpages/man1/cda2dcm.1
+           doxygen/manpages/man1/dcm2json.1
+           doxygen/manpages/man1/dcm2pdf.1
+           doxygen/manpages/man1/dcm2pnm.1
+           doxygen/manpages/man1/dcm2xml.1
+           doxygen/manpages/man1/dcmcjpeg.1
+           doxygen/manpages/man1/dcmcjpls.1
+           doxygen/manpages/man1/dcmconv.1
+           doxygen/manpages/man1/dcmcrle.1
+           doxygen/manpages/man1/dcmdjpeg.1
+           doxygen/manpages/man1/dcmdjpls.1
+           doxygen/manpages/man1/dcmdrle.1
+           doxygen/manpages/man1/dcmdspfn.1
+           doxygen/manpages/man1/dcmdump.1
+           doxygen/manpages/man1/dcmftest.1
+           doxygen/manpages/man1/dcmgpdir.1
+           doxygen/manpages/man1/dcmicmp.1
+           doxygen/manpages/man1/dcmj2pnm.1
+           doxygen/manpages/man1/dcml2pnm.1
+           doxygen/manpages/man1/dcmmkcrv.1
+           doxygen/manpages/man1/dcmmkdir.1
+           doxygen/manpages/man1/dcmmklut.1
+           doxygen/manpages/man1/dcmodify.1
+           doxygen/manpages/man1/dcmp2pgm.1
+           doxygen/manpages/man1/dcmprscp.1
+           doxygen/manpages/man1/dcmprscu.1
+           doxygen/manpages/man1/dcmpschk.1
+           doxygen/manpages/man1/dcmpsmk.1
+           doxygen/manpages/man1/dcmpsprt.1
+           doxygen/manpages/man1/dcmpsrcv.1
+           doxygen/manpages/man1/dcmpssnd.1
+           doxygen/manpages/man1/dcmqridx.1
+           doxygen/manpages/man1/dcmqrscp.1
+           doxygen/manpages/man1/dcmqrti.1
+           doxygen/manpages/man1/dcmquant.1
+           doxygen/manpages/man1/dcmrecv.1
+           doxygen/manpages/man1/dcmscale.1
+           doxygen/manpages/man1/dcmsend.1
+           doxygen/manpages/man1/dcmsign.1
+           doxygen/manpages/man1/dcod2lum.1
+           doxygen/manpages/man1/dconvlum.1
+           doxygen/manpages/man1/drtdump.1
+           doxygen/manpages/man1/dsr2html.1
+           doxygen/manpages/man1/dsr2xml.1
+           doxygen/manpages/man1/dsrdump.1
+           doxygen/manpages/man1/dump2dcm.1
+           doxygen/manpages/man1/echoscu.1
+           doxygen/manpages/man1/findscu.1
+           doxygen/manpages/man1/getscu.1
+           doxygen/manpages/man1/img2dcm.1
+           doxygen/manpages/man1/movescu.1
+           doxygen/manpages/man1/pdf2dcm.1
+           doxygen/manpages/man1/stl2dcm.1
+           doxygen/manpages/man1/storescp.1
+           doxygen/manpages/man1/storescu.1
+           doxygen/manpages/man1/termscu.1
+           doxygen/manpages/man1/wlmscpfs.1
+           doxygen/manpages/man1/xml2dcm.1
+           doxygen/manpages/man1/xml2dsr.1
+
+**** Changes from 2020.12.29 (eichelberg)
+
+- Minor bug fixes in dcmpsprt application.
+  The --img-request-size option now works correctly when the target printer
+  is not explicitly specified with --printer. Furthermore, the --overlay
+  option now correctly processes PBM files with no whitespace between digits.
+  Affects: dcmpstat/apps/dcmpsprt.cc
+
+- Fixed annotation layout.
+  Affects: dcmpstat/libsrc/dviface.cc
+
+**** Changes from 2020.12.27 (eichelberg)
+
+- Fixed socket handling in dcmpsrcv.
+  Fixed the handling of the accepted socket in the parent process when running
+  dcmpsrcv on a Posix platform. The parent process did not properly close the
+  socket, causing the transport connection to stay open after an A-ABORT, which
+  in turn led to a long timeout in storescu.
+  Affects: dcmpstat/apps/dcmpsrcv.cc
+
+**** Changes from 2020.12.15 (riesmeier)
+
+- Fixed wrong calculation of sigmoid VOI function.
+  Fixed possibly wrong output of sigmoid VOI LUT function, e.g. when
+  processing an image with a photometric interpretation of MONOCHROME1
+  (i.e. inverse). The original formula in the DICOM standard was incorrect
+  and has been fixed only recently with CP-1880.
+  Please note that the issue was only present when no presentation LUT or
+  display calibration was enabled (case #6 and #8 of the monochrome "VOI
+  SIGMOID" rendering algorithm).
+  Thanks to Robert Mulcahey <rob@asteris.com> for the report and suggested fix.
+  Affects: dcmimgle/include/dcmtk/dcmimgle/dimoopxt.h
+
+- Introduced local constant "lowvalue" for typecast.
+  This is just a preparatory step for the subsequent commit.
+  Affects: dcmimgle/include/dcmtk/dcmimgle/dimoopxt.h
+
+**** Changes from 2020.12.07 (eichelberg)
+
+- Fixed bug in dcmscale:
+  Fixed bug in dcmscale where a pointer was not checked for NULL.
+  This could cause a segmentation fault specifically if DCMTK was compiled
+  with DCMTK_ENABLE_STL and the source image contained an empty
+  DerivationDescription attribute.
+  Affects: dcmimage/apps/dcmscale.cc
+
+**** Changes from 2020.11.27 (riesmeier)
+
+- Added missing DCMTK module "dcmect".
+  Affects: README
+           README.md
+
+**** Changes from 2020.11.25 (riesmeier)
+
+- Added definition of new Storage SOP Class UID:
+  Updated list of Storage SOP Class UIDs known to the DCMTK based on DICOM
+  2020e. This includes the Final Text version of Supplement 221 (Dermoscopy).
+  Affects: dcmdata/include/dcmtk/dcmdata/dcuid.h
+           dcmdata/libsrc/dcuid.cc
+           dcmnet/docs/movescu.man
+           dcmnet/docs/storescp.man
+           dcmnet/etc/storescp.cfg
+           dcmnet/etc/storescu.cfg
+           dcmqrdb/docs/dcmqrscp.man
+           dcmqrdb/etc/dcmqrprf.cfg
+
+- Updated Context Group classes for DICOM 2020e:
+  Updated automatically generated Context Group classes for the 2020e edition
+  of the DICOM standard. All supported classes were updated, even though there
+  were no changes to most of them.
+  Affects: dcmsr/include/dcmtk/dcmsr/cmr/cid100.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid10013.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid10033.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid11.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid244.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid29.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4020.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4021.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4031.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid42.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid6147.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7021.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7181.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7445.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7452.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7453.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7464.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7469.h
+           dcmsr/libcmr/cid100.cc
+           dcmsr/libcmr/cid10013.cc
+           dcmsr/libcmr/cid10033.cc
+           dcmsr/libcmr/cid11.cc
+           dcmsr/libcmr/cid244.cc
+           dcmsr/libcmr/cid29.cc
+           dcmsr/libcmr/cid4020.cc
+           dcmsr/libcmr/cid4021.cc
+           dcmsr/libcmr/cid4031.cc
+           dcmsr/libcmr/cid42.cc
+           dcmsr/libcmr/cid6147.cc
+           dcmsr/libcmr/cid7021.cc
+           dcmsr/libcmr/cid7181.cc
+           dcmsr/libcmr/cid7445.cc
+           dcmsr/libcmr/cid7452.cc
+           dcmsr/libcmr/cid7453.cc
+           dcmsr/libcmr/cid7464.cc
+           dcmsr/libcmr/cid7469.cc
+
+- Updated code definitions for DICOM 2020e:
+  Updated automatically generated code definitions for coding schemes "DCM",
+  "NCIt" and "UMLS".
+  Affects: dcmsr/include/dcmtk/dcmsr/codes/dcm.h
+           dcmsr/include/dcmtk/dcmsr/codes/ncit.h
+           dcmsr/include/dcmtk/dcmsr/codes/umls.h
+
+**** Changes from 2020.11.24 (riesmeier)
+
+- Updated data dictionary for DICOM 2020e:
+  Updated data dictionary for the latest edition of the DICOM standard,
+  which has been released only recently.
+  Affects: dcmdata/data/dicom.dic
+           dcmdata/include/dcmtk/dcmdata/dcdeftag.h
+           dcmdata/libsrc/dcdictbi.cc
+
+**** Changes from 2020.11.23 (riesmeier)
+
+- Removed superfluous code line:
+  Removed superfluous code line that could lead to namespace clashes with
+  other libraries, e.g. Qt.
+  Thanks to Adrian Schmidt-Foehre <A.Schmidt-Foehre@mint-medical.de> for
+  the report.
+  Affects: dcmseg/include/dcmtk/dcmseg/segtypes.h
+
+**** Changes from 2020.11.17 (eichelberg)
+
+- Fixed minor Sun Studio compiler warnings.
+  Affects: dcmect/tests/t_huge_concat.cc
+           dcmect/tests/t_roundtrip.cc
+
+- Added typecast required due to commit #09e11a591:
+  Added another typecast to logger call required due to the changes
+  introduced with commit #09e11a591.
+  Affects: dcmnet/libsrc/dulfsm.cc
+
+**** Changes from 2020.11.16 (eichelberg)
+
+- Fixed memory leak:
+  Fixed memory leak in SiCertificateVerifier::addUntrustedCertificateFile().
+  Affects: dcmsign/libsrc/sicertvf.cc
+
+- Added typecast required due to commit #09e11a591:
+  Added typecast to logger call required due to the changes introduced
+  with commit #09e11a591.
+  Affects: dcmnet/libsrc/dulfsm.cc
+
+**** Changes from 2020.11.13 (eichelberg)
+
+- Properly quote special characters in person names:
+  Properly quote special characters in person names when converting DICOM
+  to XML using the native model (dcm2xml -nat).
+  This closes DCMTK issue #939.
+  Affects: dcmdata/libsrc/dcvrpn.cc
+
+- Declared finite state machine variables as volatile:
+  Declared the DICOM upper layer finite state machine variables as volatile.
+  Needed by SunPro Studio compilers when optimizing with level -xO3 or higher.
+  Affects: dcmnet/libsrc/dulfsm.cc
+
+- Disabled atof unit test related to underflow:
+  Disabled atof unit test that tests how underflow is handled since this
+  test incorrectly fails on some platforms that support denormalized
+  floating point numbers.
+  Affects: ofstd/tests/tatof.cc
+
+**** Changes from 2020.11.13 (riesmeier)
+
+- Remove unwanted files created by Doxygen:
+  Remove unwanted files created by Doxygen when calling "make man"
+  (Autoconf). This also makes sure that these files are not installed
+  when calling "make install".
+  Affects: doxygen/Makefile.in
+
+- Updated latest tested CMake version:
+  Updated information on latest CMake version that has been tested to "3.18.4".
+  Affects: CMake/dcmtkPrepare.cmake
+
+**** Changes from 2020.11.12 (riesmeier)
+
+- Renamed libcharls also for Autoconf build system:
+  Renamed libcharls (to libdcmtkcharls) also for the Autoconf build system.
+  See commit 46b4b4c, which made this change for the CMake build system.
+  Affects: dcmjpls/apps/Makefile.in
+           dcmjpls/libcharls/Makefile.in
+           dcmnet/apps/Makefile.in
+
+**** Changes from 2020.11.11 (eichelberg)
+
+- First draft of ANNOUNCE file for DCMTK 3.6.6.
+  Affects: ANNOUNCE
+
+- Updated DIMSE compatibility flag.
+  Affects: dcmnet/include/dcmtk/dcmnet/dul.h
+
+**** Changes from 2020.11.10 (eichelberg)
+
+- Renamed libcharls to libdcmtkcharls:
+  Renamed the CharLS JPEG-LS library that is built into DCMTK from
+  "charls" to "dcmtkcharls" to avoid a naming conflict with another
+  installation of the CharLS library when building shared libraries.
+  Thanks to Mathieu Malaterre <malat@debian.org> for the suggestion
+  and the patch.
+  Affects: dcmjpls/apps/CMakeLists.txt
+           dcmjpls/libcharls/CMakeLists.txt
+           dcmjpls/libcharls/intrface.h
+           dcmjpls/libsrc/CMakeLists.txt
+
+**** Changes from 2020.11.03 (riesmeier)
+
+- Fixed issue with placeholders (--exec-on-eostudy):
+  Fixed issue with placeholders not being populated for the --exec-on-eostudy
+  option when receiving the first batch of images.
+  This issue was apparently introduced with commit 26441a226, when fixing
+  another issue regarding the use of --exec-on-eostudy together with --fork.
+  Thanks to Andreas Keizers <an-kei@web.de> for reporting this issue.
+  This closes DCMTK Bug #880.
+  Affects: dcmnet/apps/storescp.cc
+
+**** Changes from 2020.10.29 (riesmeier)
+
+- Output debug message on UN conversion:
+  Output debug message when VR of data element is reverted from "UN" to the
+  real value representation, e.g. when calling dcmdump or dcmconv with option
+  --convert-un.
+  Affects: dcmdata/libsrc/dcitem.cc
+
+**** Changes from 2020.10.20 (riesmeier)
+
+- Replaced "http" by "https".
+  Affects: README.md
+
+**** Changes from 2020.10.17 (riesmeier)
+
+- Fixed typo introduced with previous commit.
+  Affects: dcmnet/docs/dcmrecv.man
+           dcmnet/docs/echoscu.man
+           dcmnet/docs/findscu.man
+           dcmnet/docs/storescp.man
+           dcmnet/docs/storescu.man
+           dcmtls/docs/certstor.txt
+           dcmtls/libsrc/tlsopt.cc
+
+**** Changes from 2020.10.16 (eichelberg)
+
+- Fixed inconsistencies in man page and help text.
+  Affects: dcmnet/docs/dcmrecv.man
+           dcmnet/docs/echoscu.man
+           dcmnet/docs/findscu.man
+           dcmnet/docs/storescp.man
+           dcmnet/docs/storescu.man
+           dcmsign/apps/dcmsign.cc
+           dcmsign/docs/dcmsign.man
+           dcmtls/docs/certstor.txt
+           dcmtls/libsrc/tlsopt.cc
+
+**** Changes from 2020.10.13 (riesmeier)
+
+- Increased buffer size for use of sprintf():
+  Increased buffer size for use of sprintf() in order to avoid possible buffer
+  overflow reported by gcc 10.2.0 with option -Wformat-overflow, which is enabled
+  by default on Ubuntu 20.04 Linux.
+  Affects: dcmpstat/libsrc/dviface.cc
+
+**** Changes from 2020.10.07 (eichelberg)
+
+- Disable Fiber Local Storage on MinGW:
+  Disable the use of Fiber Local Storage functions on MinGW, where these
+  are not supported. Use Thread Local Storage instead.
+  Affects: oflog/include/dcmtk/oflog/thread/impl/tls.h
+
+**** Changes from 2020.10.06 (eichelberg)
+
+- Fixed incorrect static cast:
+  Fixed static cast that can be incorrect when compressed pixel data are handled.
+  Error reported by the gcc address sanitizer (-fsanitize=address).
+  Affects: dcmdata/libsrc/dcsequen.cc
+
+- Added quotes for two variables in DCMTKTargets.cmake:
+  The values of DCMTK_CMAKE_CXX_COMPILER and DCMTK_CMAKE_INSTALL_PREFIX
+  are now quoted in DCMTKTargets.cmake, in order to avoid CMake warnings
+  that are issued when the file is included and the path names contain
+  space characters (which is the default on Windows).
+  Affects: CMake/DCMTKConfig.cmake.in
+
+**** Changes from 2020.10.05 (onken)
+
+- Fixed optionality of Image Type atribute:
+  Thanks to Sergey Razuvaev <Sergey.Razuvaev@waveaccess.ru> for the
+  report.
+  Affects: dcmiod/libsrc/modgeneralimage.cc
+
+**** Changes from 2020.10.01 (schlamelcher)
+
+- Harmonized documentation of calcElementLength():
+  The documentation of calcElementLength() is now the same for DcmObject and all
+  derived classes, so you will always get all the information about how the
+  function might behave in any case, no matter where you look.
+  This closes issue #857.
+  Affects: dcmdata/include/dcmtk/dcmdata/dcitem.h
+           dcmdata/include/dcmtk/dcmdata/dcobject.h
+           dcmdata/include/dcmtk/dcmdata/dcpixel.h
+           dcmdata/include/dcmtk/dcmdata/dcsequen.h
+
+**** Changes from 2020.09.28 (riesmeier)
+
+- Updated Context Group classes for DICOM 2020d:
+  Updated automatically generated Context Group classes for the 2020d edition
+  of the DICOM standard. All supported classes were updated, even though there
+  were no changes to most of them.
+  Affects: dcmsr/include/dcmtk/dcmsr/cmr/cid100.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid10013.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid10033.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid11.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid244.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid29.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4020.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4021.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4031.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid42.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid6147.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7021.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7181.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7445.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7452.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7453.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7464.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7469.h
+           dcmsr/libcmr/cid100.cc
+           dcmsr/libcmr/cid10013.cc
+           dcmsr/libcmr/cid10033.cc
+           dcmsr/libcmr/cid11.cc
+           dcmsr/libcmr/cid244.cc
+           dcmsr/libcmr/cid29.cc
+           dcmsr/libcmr/cid4020.cc
+           dcmsr/libcmr/cid4021.cc
+           dcmsr/libcmr/cid4031.cc
+           dcmsr/libcmr/cid42.cc
+           dcmsr/libcmr/cid6147.cc
+           dcmsr/libcmr/cid7021.cc
+           dcmsr/libcmr/cid7181.cc
+           dcmsr/libcmr/cid7445.cc
+           dcmsr/libcmr/cid7452.cc
+           dcmsr/libcmr/cid7453.cc
+           dcmsr/libcmr/cid7464.cc
+           dcmsr/libcmr/cid7469.cc
+
+- Updated code definitions for DICOM 2020d:
+  Updated automatically generated code definitions for coding scheme "DCM".
+  For the coding scheme "NCIt" and "UMLS", there were no changes.
+  Affects: dcmsr/include/dcmtk/dcmsr/codes/dcm.h
+           dcmsr/include/dcmtk/dcmsr/codes/ncit.h
+           dcmsr/include/dcmtk/dcmsr/codes/umls.h
+
+- Updated data dictionary for DICOM 2020d:
+  Updated data dictionary for the latest edition of the DICOM standard.
+  Affects: dcmdata/data/dicom.dic
+           dcmdata/include/dcmtk/dcmdata/dcdeftag.h
+           dcmdata/libsrc/dcdictbi.cc
+
+**** Changes from 2020.09.25 (riesmeier)
+
+- Added reference to further documentation (HTML):
+  Added reference to further documentation on "Certification Authority (CA)
+  Certificate Management in DCMTK" (file "dcmtls/docs/certstor.txt").
+  Affects: dcmtls/docs/certstor.txt
+           dcmtls/docs/dcmtls.dox
+
+**** Changes from 2020.09.22 (riesmeier)
+
+- Added new well-known Frame of Reference UIDs:
+  Added well-known Frame of Reference UIDs from CP-2002 (Add to well known
+  brain atlas frames of reference).
+  Affects: dcmdata/include/dcmtk/dcmdata/dcuid.h
+           dcmdata/libsrc/dcuid.cc
+
+**** Changes from 2020.09.17 (riesmeier)
+
+- Updated latest tested CMake version:
+  Updated information on latest CMake version that has been tested to "3.18.2".
+  Affects: CMake/dcmtkPrepare.cmake
+
+**** Changes from 2020.09.17 (onken)
+
+- Fixed access to Depths Of Scan Field attribute:
+  Thanks to Sergey Razuvaev <Sergey.Razuvaev@waveaccess.ru> for the report
+  and suggested fix.
+  Affects: dcmiod/include/dcmtk/dcmiod/modenhusimage.h
+           dcmiod/libsrc/modenhusimage.cc
+
+**** Changes from 2020.09.13 (eichelberg)
+
+- Fixed use-after-free error in worklist SCP:
+  Fixed use-after-free error in WlmActivityManager::RemoveProcessFromTable
+  reported by the gcc address sanitizer (-fsanitize=address).
+  Affects: dcmwlm/libsrc/wlmactmg.cc
+
+- Fixed out-of-bound read in parseSCUSCPRole():
+  Fixed an out-of-bounds read access that could be caused by a malformed
+  A-ASSOCIATE packet.
+  Thanks to Matthias Gierlings <matthias.gierlings@ruhr-uni-bochum.de>
+  for the bug report.
+  This closes DCMTK issue #942.
+  Affects: dcmnet/libsrc/dulparse.cc
+
+**** Changes from 2020.09.11 (eichelberg)
+
+- Clean-up of dcmsign exit codes (cont'd).
+  Added:   dcmsign/include/dcmtk/dcmsign/siexit.h
+
+**** Changes from 2020.09.11 (riesmeier)
+
+- Extended range of application-specific errors:
+  Extended range of application-specific / user-defined errors. Now, the
+  exit codes 120 to 127 also belong to this group.
+  Affects: ofstd/include/dcmtk/ofstd/ofexit.h
+
+- Fixed line indentation.
+  Affects: config/docs/macros.txt
+           dcmdata/include/dcmtk/dcmdata/dcelem.h
+
+**** Changes from 2020.09.11 (eichelberg)
+
+- Fixed typo.
+  Affects: config/docs/macros.txt
+           config/tests/arith.cc
+
+- Added new compile time macro DCMTK_UNDEF_SANIZITER:
+  Added new compile time macro DCMTK_UNDEF_SANIZITER that allows DCMTK to
+  be compiled with the gcc undefined behavior sanitizer (-fsanitize=undefined)
+  without the need to manually modify config/tests/arith.cc.
+  Affects: config/docs/macros.txt
+           config/tests/arith.cc
+
+- Clean-up of dcmsign exit codes:
+  Changed declaration file and values of dcmsign exit codes for better
+  consistency with the overall toolkit.
+  Affects: dcmsign/apps/dcmsign.cc
+           dcmsign/docs/dcmsign.man
+           dcmsign/include/dcmtk/dcmsign/sitypes.h
+           dcmsign/libsrc/dcsighlp.cc
+
+**** Changes from 2020.09.11 (riesmeier)
+
+- Added comments and check options in right order.
+  Affects: dcmwlm/apps/wlcefs.cc
+
+- Removed empty line.
+  Affects: dcmwlm/docs/wlmscpfs.man
+
+**** Changes from 2020.09.11 (onken)
+
+- Moved 2 options from processing to output section:
+  The following options are now in section "output" rather than
+  "processing":
+    -rfp  --request-file-path  [p]ath: string
+            path to store request files to
+    -rff  --request-file-format  [f]ormat: string (default: #t.dump)
+            request file name format
+  Affects: dcmwlm/apps/wlcefs.cc
+           dcmwlm/docs/wlmscpfs.man
+
+**** Changes from 2020.09.09 (riesmeier)
+
+- Fixed wrong use of doxygen markup in manpage.
+  Affects: dcmdata/docs/dcm2json.man
+
+**** Changes from 2020.09.08 (riesmeier)
+
+- Fixed wrong variable being read:
+  Fixed wrong variable being read in IODEnhUSImageModule::read().
+  Thanks to Sergey Razuvaev <Sergey.Razuvaev@waveaccess.ru> for the report
+  and suggested fix.
+  Affects: dcmiod/libsrc/modenhusimage.cc
+
+- Fixed duplicate value of an error code:
+  With the previous commit, the existing dcmdata error code 55 was reused.
+  Affects: dcmdata/libsrc/dcerror.cc
+
+**** Changes from 2020.09.08 (eichelberg)
+
+- Fixed JSON InlineBinary pixel data encoding:
+  Implemented a new method DcmPixelData::writeJson() that properly handles
+  the InlineBinary JSON encoding of DICOM pixel data, which is not supported
+  in the DICOM JSON model for encapsulated (compressed) images. Instead of
+  silently writing an empty pixel data element, we now report an error.
+  Together with various previous commits, this closes DCMTK issue #881.
+  Affects: dcmdata/include/dcmtk/dcmdata/dcerror.h
+           dcmdata/include/dcmtk/dcmdata/dcpixel.h
+           dcmdata/libsrc/dcerror.cc
+           dcmdata/libsrc/dcpixel.cc
+
+- Minor fixes to dcm2json man page and help output.
+  Affects: dcmdata/apps/dcm2json.cc
+           dcmdata/docs/dcm2json.man
+
+**** Changes from 2020.09.03 (eichelberg)
+
+- Fix compilation on platforms where isinf is a macro:
+  Fix compilation on platforms such as OpenIndiana with STL where
+  isinf() and isnan() are defined as macros.
+  Affects: dcmdata/libsrc/dcvrfd.cc
+           dcmdata/libsrc/dcvrfl.cc
+
+**** Changes from 2020.09.02 (eichelberg)
+
+- Further improvements and fixes to dcm2json:
+  For the DS, IS, SV, and UV value representation, the decision to encode
+  as JSON number or string is now made for each value, not the entire
+  attribute. Furthermore, InlineBinary is now always encoded in little
+  endian byte order.
+  Affects: dcmdata/libsrc/dcjson.cc
+           dcmdata/libsrc/dcvrds.cc
+           dcmdata/libsrc/dcvris.cc
+           dcmdata/libsrc/dcvrobow.cc
+           dcmdata/libsrc/dcvrod.cc
+           dcmdata/libsrc/dcvrof.cc
+           dcmdata/libsrc/dcvrol.cc
+           dcmdata/libsrc/dcvrov.cc
+           dcmdata/libsrc/dcvrsv.cc
+           dcmdata/libsrc/dcvruv.cc
+
+**** Changes from 2020.09.02 (riesmeier)
+
+- Improved documentation of option --grayscale:
+  Thanks to GitHub user "malaterre" for the hint and the original patch.
+  Affects: dcmimage/apps/dcm2pnm.cc
+           dcmimage/docs/dcm2pnm.man
+           dcmjpeg/docs/dcmj2pnm.man
+           dcmjpls/docs/dcml2pnm.man
+
+- Added structure to documented "exit codes":
+  Added typical structure of DCMTK's command line tools to the documented
+  "exit code" of dcm2json. Also added missing exit codes to the manpage.
+  Affects: dcmdata/docs/dcm2json.man
+
+- Fixed wrong capitalization of the acronym "JSON".
+  Affects: dcmdata/apps/dcm2json.cc
+           dcmdata/docs/dcm2json.man
+           dcmdata/include/dcmtk/dcmdata/dcerror.h
+           dcmdata/include/dcmtk/dcmdata/dcjson.h
+           dcmdata/libsrc/dcerror.cc
+           dcmdata/libsrc/dcvrfd.cc
+           dcmdata/libsrc/dcvrfl.cc
+
+**** Changes from 2020.09.01 (eichelberg)
+
+- Various enhancements to dcm2json:
+  The dcm2json tool now returns well-defined error codes when terminating.
+  Furthermore, the handling of DICOM FL/FD elements with values that are
+  infinity or not a number can now be defined by a command line option.
+  Affects: dcmdata/apps/dcm2json.cc
+           dcmdata/docs/dcm2json.man
+           dcmdata/include/dcmtk/dcmdata/dcerror.h
+           dcmdata/include/dcmtk/dcmdata/dcjson.h
+           dcmdata/include/dcmtk/dcmdata/dcvrfd.h
+           dcmdata/include/dcmtk/dcmdata/dcvrfl.h
+           dcmdata/libsrc/dcerror.cc
+           dcmdata/libsrc/dcvrfd.cc
+           dcmdata/libsrc/dcvrfl.cc
+
+**** Changes from 2020.08.31 (eichelberg)
+
+- Fixed Json control char escaping in PN VR:
+  dcm2json now properly escapes control characters, quotation marks etc.
+  in Person Names when converting DICOM to Json.
+  Thanks to DCMTK forum user Shaeto for the bug report.
+  This closes the Json related part of DCMTK issue #939.
+  Affects: dcmdata/libsrc/dcvrpn.cc
+
+**** Changes from 2020.08.24 (riesmeier)
+
+- Added support for new Waveform Storage SOP Classes:
+  Added support for new Waveform Storage SOP Classes, introduced with
+  Supplement 217 (Neurophysiology Waveforms), to the DICOMDIR generation
+  code and to the Structured Reporting module "dcmsr".
+  Affects: dcmdata/libsrc/dcddirif.cc
+           dcmsr/include/dcmtk/dcmsr/dsrwavvl.h
+           dcmsr/libsrc/dsrwavvl.cc
+
+- Updated reference to current standard edition:
+  Updated reference to the current edition of the DICOM standard (2020c).
+  Affects: dcmsr/include/dcmtk/dcmsr/dsrimgvl.h
+           dcmsr/libsrc/dsrimgvl.cc
+
+**** Changes from 2020.08.10 (riesmeier)
+
+- Removed superfluous call of empty() method:
+  Removed superfluous call of OFVector<>::empty() method in destructor. This
+  makes the message "warning C4834: discarding return value of function with
+  'nodiscard' attribute" reported by VisualStudio 2019 disappear.
+  Affects: dcmjpls/libcharls/header.cc
+
+**** Changes from 2020.08.06 (riesmeier)
+
+- Enhanced documentation of --recognize-aspect.
+  Affects: dcmimage/apps/dcmscale.cc
+           dcmimage/docs/dcmscale.man
+
+**** Changes from 2020.08.05 (riesmeier)
+
+- Added "Software" field to created TIFF images:
+  Added "Software" field to created TIFF images and changed first letter
+  of "Image Description" to upper case in order to be more consistent
+  with meta information of created PNG images.
+  Thanks to GitHub user "malaterre" for the original patch.
+  Affects: dcmimage/libsrc/dipitiff.cc
+
+**** Changes from 2020.08.03 (riesmeier)
+
+- Enhanced documentation of --recognize-aspect:
+  Enhanced documentation of the --recognize-aspect option, i.e. make clear that
+  it is only evaluated when actually scaling an image.
+  Thanks to Mathieu Malaterre <mathieu.malaterre@gmail.com> for the hint.
+  Affects: dcmimage/apps/dcm2pnm.cc
+           dcmimage/docs/dcm2pnm.man
+           dcmjpeg/docs/dcmj2pnm.man
+           dcmjpls/docs/dcml2pnm.man
+
+**** Changes from 2020.07.31 (riesmeier)
+
+- Output debug information when changing the VR:
+  Output debug information to the logger when changing the VR to UN (or OB)
+  because the maximum value that can be stored in a 16-bit length field is
+  exceeded.
+  See CP-1066 and commit bb022b4 for further details.
+  Affects: dcmdata/libsrc/dcelem.cc
+           dcmdata/libsrc/dcobject.cc
+
+- Added basic support for leap second:
+  Now, a time value with 60 seconds is accepted (not only for 23:59:60).
+  However, calculations bases on such a time value might be incorrect.
+  Background: the DICOM standard explicitly allows TM and DT values to
+  store a value of "60" for the "SS" (seconds) component.
+  Affects: ofstd/include/dcmtk/ofstd/ofdatime.h
+           ofstd/include/dcmtk/ofstd/oftime.h
+           ofstd/libsrc/oftime.cc
+           ofstd/tests/tofdatim.cc
+
+**** Changes from 2020.07.29 (riesmeier)
+
+- Removed superfluous code line:
+  Removed superfluos code line to get rid of a warning reported by Visual
+  Studio 2019: "warning C4834: discarding return value of function with
+  'nodiscard' attribute".
+  Affects: dcmiod/libsrc/iodmacro.cc
+
+**** Changes from 2020.07.28 (riesmeier)
+
+- Updated copyright date (where applicable):
+  Updated copyright date (where applicable) and added separator lines to the
+  text to better distinguish the individual sections.
+  Affects: COPYRIGHT
+
+**** Changes from 2020.07.27 (riesmeier)
+
+- Added explicit typecast to keep VS 2019 quiet:
+  Added explicit typecast to integer variable in order to keep VisualStudio
+  2019 quiet.
+  Affects: dcmdata/libsrc/dcencdoc.cc
+
+- Made use of OFswap() in class OFFilename:
+  Made use of OFswap() instead of a local variable when swapping the value
+  of two member variables, in this case the internal representation of a
+  filename.
+  Affects: ofstd/libsrc/offile.cc
+
+- Enhanced support for OFpath filenames:
+  Enhanced support for passing an OFpath instance to the OFFilename class.
+  Now, the optional "convert" parameter is handled in the same way as for
+  other input types (such as char* or OFString).
+  Affects: ofstd/include/dcmtk/ofstd/offile.h
+           ofstd/libsrc/offile.cc
+
+- Fixed wrong position of a remark.
+  Affects: ofstd/include/dcmtk/ofstd/offile.h
+
+**** Changes from 2020.07.17 (riesmeier)
+
+- Fixed issue with invalid length of user item:
+  Fixed issue with an invalid value in the item-length field of the Maximum
+  Length Sub-Item Structure (A-ASSOCIATE-RQ). In case of a malformed
+  association request, the non-existent test on the item-length value could
+  result in a crash (segmentation fault).
+  Now, the value in the item-length field of this sub-item type (51h) is
+  checked (similar to the check for the other sub-items).
+  Thanks to Maria Nedyak <mashanedyak@gmail.com> for the bug report as well
+  as the test data and script that allowed for reproducing this issue.
+  Affects: dcmnet/libsrc/dulparse.cc
+
+**** Changes from 2020.07.16 (riesmeier)
+
+- Various fixes to API documentation.
+  Affects: dcmnet/libsrc/dulparse.cc
+
+**** Changes from 2020.07.10 (riesmeier)
+
+- Fixed outdated reference to default option:
+  Option --write-file is no longer the default in section "output file format".
+  Affects: dcmdata/docs/dcmconv.man
+
+- Removed obsolete lines from code example.
+  Affects: dcmjpeg/docs/dcmjpeg.dox
+           dcmjpls/docs/dcmjpls.dox
+
+- Minor fixes to manpage:
+  Fixed doxygen markup and typos. Also made sure that always the long version
+  of an option is used when referring to a command line option in the text.
+  Affects: dcmdata/docs/cda2dcm.man
+           dcmdata/docs/img2dcm.man
+           dcmdata/docs/pdf2dcm.man
+           dcmdata/docs/stl2dcm.man
+
+**** Changes from 2020.07.09 (arizpegomez)
+
+- Improved documentation of --key option:
+  Improved and unified the documentation of the --key option for the apps in
+  dcmdata.
+  This closes DCMTK issue #889.
+  Affects: .gitignore
+           dcmdata/docs/cda2dcm.man
+           dcmdata/docs/img2dcm.man
+           dcmdata/docs/pdf2dcm.man
+           dcmdata/docs/stl2dcm.man
+
+**** Changes from 2020.07.09 (onken)
+
+- New default to always re-create meta header:
+  The default behavior of DCMTK when writing DICOM files was to re-use
+  existing meta header information. This can lead to problems if essential
+  information in the dataset (like SOP Instance UID) changes without
+  explicitly enforcing those changes in the meta header, too.
+  By always re-creating the complete meta header it is ensured that all
+  its attributes are up-to-date and complete.
+  Affects: dcmdata/apps/dcmconv.cc
+           dcmdata/apps/img2dcm.cc
+           dcmdata/apps/mdfdsman.cc
+           dcmdata/docs/dcmconv.man
+           dcmdata/include/dcmtk/dcmdata/dcfilefo.h
+           dcmimage/apps/dcmquant.cc
+           dcmimage/apps/dcmscale.cc
+           dcmjpeg/apps/dcmdjpeg.cc
+           dcmjpls/apps/dcmdjpls.cc
+           dcmnet/apps/movescu.cc
+
+**** Changes from 2020.07.09 (schlamelcher)
+
+- Allow overriding support library search behaviour:
+  Added two new CMake cache variables to control the way DCMTK looks for
+  support libraries on Windows:
+    DCMTK_USE_FIND_PACKAGE: defaults to FALSE on Windows except MinGW
+    DCMTK_SUPPORT_LIBRARIES_DIR: defaults to parent of main source directory
+  On all other platforms, find_package() will be used as before, ignoring any
+  potential user choice of this setting.
+  Affects: CMake/3rdparty.cmake
+
+**** Changes from 2020.07.08 (riesmeier)
+
+- Updated mapping of Body Part Examined to codes:
+  Updated mapping of the Defined Terms for Body Part Examined (0018,0015) to
+  associated CID 4031 (Common Anatomic Regions) codes based on PS3.16 Table
+  L-1 (2020c edition of the DICOM standard).
+  Affects: dcmsr/libcmr/cid4031e.cc
+
+- Updated Context Group classes for DICOM 2020c:
+  Updated automatically generated Context Group classes for the 2020c edition
+  of the DICOM standard. All supported classes were updated, even though there
+  were no changes to most of them.
+  Affects: dcmsr/include/dcmtk/dcmsr/cmr/cid100.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid10013.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid10033.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid11.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid244.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid29.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4020.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4021.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4031.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid42.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid6147.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7021.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7181.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7445.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7452.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7453.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7464.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7469.h
+           dcmsr/libcmr/cid100.cc
+           dcmsr/libcmr/cid10013.cc
+           dcmsr/libcmr/cid10033.cc
+           dcmsr/libcmr/cid11.cc
+           dcmsr/libcmr/cid244.cc
+           dcmsr/libcmr/cid29.cc
+           dcmsr/libcmr/cid4020.cc
+           dcmsr/libcmr/cid4021.cc
+           dcmsr/libcmr/cid4031.cc
+           dcmsr/libcmr/cid42.cc
+           dcmsr/libcmr/cid6147.cc
+           dcmsr/libcmr/cid7021.cc
+           dcmsr/libcmr/cid7181.cc
+           dcmsr/libcmr/cid7445.cc
+           dcmsr/libcmr/cid7452.cc
+           dcmsr/libcmr/cid7453.cc
+           dcmsr/libcmr/cid7464.cc
+           dcmsr/libcmr/cid7469.cc
+
+- Updated code definitions for DICOM 2020c:
+  Updated automatically generated code definitions for coding scheme "DCM".
+  For the coding scheme "NCIt" and "UMLS", there were no changes.
+  Affects: dcmsr/include/dcmtk/dcmsr/codes/dcm.h
+           dcmsr/include/dcmtk/dcmsr/codes/ncit.h
+           dcmsr/include/dcmtk/dcmsr/codes/umls.h
+
+- Updated data dictionary for DICOM 2020c:
+  Updated data dictionary for the latest edition of the DICOM standard.
+  Affects: dcmdata/data/dicom.dic
+           dcmdata/include/dcmtk/dcmdata/dcdeftag.h
+           dcmdata/libsrc/dcdictbi.cc
+
+**** Changes from 2020.07.07 (eichelberg)
+
+- Fixed various issues in the Json output routines:
+  Fixed various issues in the Json output routines and the dcm2json tool:
+  - dcm2json -f now prints enclosing braces for the dataset, as it should.
+  - Fixed pretty formatting for sequences containing an empty item.
+  - Group length elements now omitted in Json output.
+  - Fixed output of IS/DS arrays larger than 4 Kbytes
+  - Now removing '+' characters, which are permitted in IS and DS values
+    in DICOM, but not in Json
+  - IS and DS attributes containing illegal values are now printed as string.
+  - UV and SV attributes are now printed as string if any value is
+    outside the range supported by Javascript, i.e. plus/minus 2^53-1.
+  Affects: dcmdata/apps/dcm2json.cc
+           dcmdata/include/dcmtk/dcmdata/dcdatset.h
+           dcmdata/include/dcmtk/dcmdata/dcfilefo.h
+           dcmdata/include/dcmtk/dcmdata/dcitem.h
+           dcmdata/include/dcmtk/dcmdata/dcvrat.h
+           dcmdata/include/dcmtk/dcmdata/dcvris.h
+           dcmdata/include/dcmtk/dcmdata/dcvrpn.h
+           dcmdata/include/dcmtk/dcmdata/dcvrsv.h
+           dcmdata/include/dcmtk/dcmdata/dcvruv.h
+           dcmdata/libsrc/dcdatset.cc
+           dcmdata/libsrc/dcfilefo.cc
+           dcmdata/libsrc/dcitem.cc
+           dcmdata/libsrc/dcjson.cc
+           dcmdata/libsrc/dcvrat.cc
+           dcmdata/libsrc/dcvrds.cc
+           dcmdata/libsrc/dcvris.cc
+           dcmdata/libsrc/dcvrsv.cc
+           dcmdata/libsrc/dcvruv.cc
+
+**** Changes from 2020.06.30 (riesmeier)
+
+- Fixed issue with attribute tag in JSON output:
+  According to PS3.18 Section F.2.2, the "name of each attribute object"
+  is "The eight character uppercase hexadecimal representation of a DICOM
+  Tag". Before, the group number was output with lowercase characters.
+  Thanks to DCMTK forum user "Shaeto" for the report.
+  Affects: dcmdata/libsrc/dcelem.cc
+
+- Check for data dictionary when needed for a test:
+  Made sure that all regression tests also work if no data dictionary is
+  loaded or report the test case as "failed" with an appropriate message
+  (if it does not work without data dictionary).
+  This closes DCMTK Bug #915.
+  Affects: dcmdata/tests/tdict.cc
+           dcmdata/tests/tfilter.cc
+           dcmdata/tests/tparser.cc
+           dcmdata/tests/tpath.cc
+           dcmdata/tests/tpread.cc
+           dcmdata/tests/tvrcomp.cc
+           dcmdata/tests/tvrdatim.cc
+           dcmdata/tests/tvrds.cc
+           dcmfg/tests/t_concatenation_loader.cc
+           dcmfg/tests/t_ct_acquisition_details.cc
+           dcmfg/tests/t_ct_acquisition_type.cc
+           dcmfg/tests/t_ct_image_frame_type.cc
+           dcmfg/tests/t_ct_position.cc
+           dcmfg/tests/t_ct_table_dynamics.cc
+           dcmfg/tests/t_deriv_image.cc
+           dcmfg/tests/t_frame_content.cc
+           dcmfg/tests/t_irradiation_event_identification.cc
+           dcmiod/tests/tcodes.cc
+           dcmnet/tests/tdump.cc
+           dcmseg/tests/troundtrip.cc
+           dcmsr/tests/tsrcmr.cc
+           dcmsr/tests/tsrcodvl.cc
+
+**** Changes from 2020.06.29 (riesmeier)
+
+- Reworked check on invalid Completion Flag (RDSR):
+  Reworked check on invalid value for Completion Flag (0040,a491) encountered
+  when reading or writing an X-Ray Radiation Dose Structured Report (RDSR).
+  However, the behavior (i.e. the output of a warning message to the logger)
+  should be identical to the previous implementation.
+  Affects: dcmsr/libsrc/dsrdoc.cc
+
+**** Changes from 2020.06.26 (riesmeier)
+
+- Added support for new Storage SOP Classes:
+  Added definition of new Storage SOP Class UIDs from Supplement 199 (Second
+  Generation Radiotherapy - RT Radiation Records) and Supplement 217
+  (Neurophysiology Waveforms).
+  This commit also adds support for the various networking tools and for
+  generating a DICOMDIR referencing objects of the underlying IODs.
+  Affects: dcmdata/include/dcmtk/dcmdata/dcuid.h
+           dcmdata/libsrc/dcddirif.cc
+           dcmdata/libsrc/dcuid.cc
+           dcmnet/docs/movescu.man
+           dcmnet/docs/storescp.man
+           dcmnet/etc/storescp.cfg
+           dcmnet/etc/storescu.cfg
+           dcmqrdb/docs/dcmqrscp.man
+           dcmqrdb/etc/dcmqrprf.cfg
+
+- Updated data dictionary for Supplement 199 + 217:
+  Updated data dictionary for recently approved changes to the DICOM standard,
+  i.e. Final Text of Supplement 199 (Second Generation Radiotherapy - RT
+  Radiation Records) and Supplement 217 (Neurophysiology Waveforms).
+  Affects: dcmdata/data/dicom.dic
+           dcmdata/include/dcmtk/dcmdata/dcdeftag.h
+           dcmdata/libsrc/dcdictbi.cc
+
+**** Changes from 2020.06.23 (riesmeier)
+
+- Output error message on missing sequence element:
+  Output error message on missing Verifying Observer Sequence element when
+  checking a DICOM file of the type "SR DOCUMENT" to be added to a DICOMDIR.
+  Previously, the file was rejected (e.g. by dcmgpdir or dcmmkdir) but the
+  reason was not given.
+  Thanks to DCMTK forum user "ruben.cruz" for the report and sample file.
+  Affects: dcmdata/libsrc/dcddirif.cc
+
+**** Changes from 2020.06.03 (riesmeier)
+
+- Added missing VRs to API documentation:
+  Added missing (mainly newer) VRs to API documentation of findAndGetXXX(),
+  putAndInsertXXX() and insertEmptyElement() methods.
+  Affects: dcmdata/include/dcmtk/dcmdata/dcitem.h
+
+**** Changes from 2020.06.02 (riesmeier)
+
+- Clarified API documentation (in case of error).
+  Affects: dcmsr/include/dcmtk/dcmsr/dsrxmld.h
+
+**** Changes from 2020.05.27 (eichelberg)
+
+- Fixed bug in handling of pixel data representations:
+  Compression and decompression codecs that may modify the DICOM dataset such
+  that the pixel data before the coding process is not consistent anymore with
+  the DICOM dataset after the coding (e.g. because planar configuration or
+  photometric interpretation may have changed) now remove the previous
+  in-memory pixel data representation.
+  Unfortunately this requires an API change in DcmCodec::encode() and
+  DcmCodec::decode() that must be implemented by all image compression codecs.
+  Thanks to Peter Klotz <peter.klotz@ith-icoserve.com> for the bug report.
+  This closes DCMTK issue #845.
+  Affects: dcmdata/include/dcmtk/dcmdata/dccodec.h
+           dcmdata/include/dcmtk/dcmdata/dcrleccd.h
+           dcmdata/include/dcmtk/dcmdata/dcrlecce.h
+           dcmdata/libsrc/dccodec.cc
+           dcmdata/libsrc/dcpixel.cc
+           dcmdata/libsrc/dcrleccd.cc
+           dcmdata/libsrc/dcrlecce.cc
+           dcmjpeg/include/dcmtk/dcmjpeg/djcodecd.h
+           dcmjpeg/include/dcmtk/dcmjpeg/djcodece.h
+           dcmjpeg/libsrc/djcodecd.cc
+           dcmjpeg/libsrc/djcodece.cc
+           dcmjpls/include/dcmtk/dcmjpls/djcodecd.h
+           dcmjpls/include/dcmtk/dcmjpls/djcodece.h
+           dcmjpls/libsrc/djcodecd.cc
+           dcmjpls/libsrc/djcodece.cc
+
+**** Changes from 2020.05.26 (riesmeier)
+
+- Fixed issue with parsing invalid meta info:
+  Fixed issue with an error being ignored (not propagated to the caller)
+  when parsing a DICOM file with an invalid meta information header.
+  Thanks to Maria Samoylova <mashanedyak@gmail.com> for the report and the
+  sample file.
+  Affects: dcmdata/libsrc/dcelem.cc
+           dcmdata/libsrc/dcmetinf.cc
+
+- Fixed name of SOP classes from Supplement 202:
+  Removed suffix "SOPClass" from the name of the SOP Classes introduced only
+  recently with Supplement 202 (Real-Time Video). The names are now consistent
+  with the official "UID Name" in DICOM PS3.6.
+  Affects: dcmdata/include/dcmtk/dcmdata/dcuid.h
+           dcmdata/libsrc/dcuid.cc
+           dcmsr/libsrc/dsrtypes.cc
+
+- Added support for new SR IOD from Supplement 202:
+  Added full support for the new Rendition Selection Document IOD introduced
+  with Supplement 202. Please note that the associated Rendition Selection
+  Document Real-Time Communication SOP Class is not a Storage SOP Class, so
+  instances of this class are not meant to be stored as files or transferred
+  over the network using the Storage Service Class.
+  Closes DCMTK Feature #926.
+  Added:   dcmsr/include/dcmtk/dcmsr/dsrrsdcc.h
+           dcmsr/libsrc/dsrrsdcc.cc
+  Affects: dcmsr/include/dcmtk/dcmsr/dsrtypes.h
+           dcmsr/libsrc/CMakeLists.txt
+           dcmsr/libsrc/Makefile.in
+           dcmsr/libsrc/dsrtypes.cc
+
+**** Changes from 2020.05.25 (onken)
+
+- Fixed doxygen and formatting.
+  Affects: dcmdata/include/dcmtk/dcmdata/dcpath.h
+           dcmdata/libsrc/dcpath.cc
+
+- Fixed bug that caused known private tag to be inserted with VR UN:
+  Thanks to forum user CStarkey for the report.
+  Affects: dcmdata/include/dcmtk/dcmdata/dcpath.h
+           dcmdata/libsrc/dcpath.cc
+
+**** Changes from 2020.05.22 (riesmeier)
+
+- Generalized support for Key Object Documents (KO):
+  Added more general support for SR IODs that contain the Key Object Document
+  Modules (on Series and Document level). This is needed since the Rendition
+  Selection Document IOD also contains these modules.
+  This is only a preparatory step for implementing support for this SR IOD
+  introduced with Supplement 202 (Real-Time Video).
+  Affects: dcmsr/include/dcmtk/dcmsr/dsrdoc.h
+           dcmsr/include/dcmtk/dcmsr/dsrtypes.h
+           dcmsr/libsrc/dsrdoc.cc
+           dcmsr/libsrc/dsrtypes.cc
+
+**** Changes from 2020.05.22 (eichelberg)
+
+- Changed declaration of tls_init_cleanup_func_type:
+  Changed declaration of tls_init_cleanup_func_type when compiling on
+  Win32. Required on Visual Studio 2010 when compiling with
+  DCMTK_LOG4CPLUS_AVOID_WIN32_FLS defined, which is needed to generate
+  binaries that run on Windows XP.
+  Thanks to Martin Czarnowski <czarnowski@examion.com> for the report.
+  Affects: oflog/include/dcmtk/oflog/thread/impl/tls.h
+
+**** Changes from 2020.05.19 (riesmeier)
+
+- Report an error if putElementContent() fails:
+  Report an error to the logger if putElementContent() fails, e.g. if the
+  element value to be set is invalid.
+  Affects: dcmdata/apps/xml2dcm.cc
+
+- Fixed documentation on "bulk data" in manpage:
+  Fixed documentation on the encoding of "bulk data" in the manpage of dcm2json.
+  Thanks to Mathieu Malaterre <mathieu.malaterre@gmail.com> for the hint.
+  This closes DCMTK Bug #928.
+  Affects: dcmdata/docs/dcm2json.man
+
+**** Changes from 2020.05.18 (eichelberg)
+
+- Fixed comment.
+  Affects: ofstd/libsrc/ofstd.cc
+
+- Fixed HUGE_VAL constant used.
+  Affects: ofstd/libsrc/ofstd.cc
+
+**** Changes from 2020.05.18 (riesmeier)
+
+- Added log output on data read from file:
+  Added log output (on both INFO and DEBUG level) when data is read from a
+  binary file, e.g. for the Pixel Data element.
+  Affects: dcmdata/apps/dump2dcm.cc
+           dcmdata/apps/xml2dcm.cc
+
+**** Changes from 2020.05.18 (eichelberg)
+
+- Documented ENABLE_EXTERNAL_DICTIONARY macro.
+  Affects: config/docs/macros.txt
+
+**** Changes from 2020.05.13 (eichelberg)
+
+- Removed JPEG-LS option for uninterleaved encoding:
+  Removed the option for uninterleaved encoding (--interleave-none) from
+  the JPEG-LS encoder on command line and library level since this option
+  may in certain cases (color image with BitsStored > 12) create
+  compressed images that are correct but cannot be decoded by the JPEG-LS
+  library due to a known bug (DCMTK issue #892). The option can be
+  re-enabled by defining the macro ENABLE_DCMJPLS_INTERLEAVE_NONE at
+  compilation time. It will be re-enabled permanently once DCMTK has been
+  ported to CharLS 2.x, another branch of the JPEG-LS library that
+  requires a C++14 compiler, however.
+  Affects: dcmjpls/apps/dcmcjpls.cc
+           dcmjpls/docs/dcmcjpls.man
+           dcmjpls/include/dcmtk/dcmjpls/djcparam.h
+           dcmjpls/libsrc/djcodece.cc
+
+**** Changes from 2020.05.04 (riesmeier)
+
+- Added UID definition of UPS Query SOP Class:
+  Added UID definition of Unified Procedure Step - Query SOP Class introduced
+  with CP-1907.
+  Affects: dcmdata/include/dcmtk/dcmdata/dcuid.h
+           dcmdata/libsrc/dcuid.cc
+
+- Added new attributes to checkMetaHeaderValue():
+  Added new attributes to DcmFileFormat::checkMetaHeaderValue() that were
+  introduced only recently with CP-1895 (i.e. SourcePresentationAddress,
+  SendingPresentationAddress and ReceivingPresentationAddress). Please note,
+  however, that this method is currently never called for these attributes.
+  Affects: dcmdata/libsrc/dcfilefo.cc
+
+**** Changes from 2020.05.01 (eichelberg)
+
+- Added alternative service provision API to DcmSCP:
+  Added alternative service provision interface to class DcmSCP that can
+  be used instead of DcmSCP::listen(). The alternative interface uses two
+  separate calls, where the first one, openListenPort(), opens the TCP
+  port and executes listen(3), and the second one, acceptAssociations(),
+  runs the service provision code just as listen() does. The alternative
+  interface allows incoming network connections to be placed on the listen
+  backlog while the caller performs other work (such as a Storage
+  Commitment SCU sending out an N-ACTION-RQ) and to be accepted and
+  handled once acceptAssociations() is run.
+  Affects: dcmnet/include/dcmtk/dcmnet/scp.h
+           dcmnet/libsrc/scp.cc
+
+**** Changes from 2020.04.24 (eichelberg)
+
+- Added text describing the maximum UID root length.
+  Affects: config/docs/macros.txt
+
+- Fixed compiler warning in VS 2008/2010 build.
+  Affects: dcmfg/include/dcmtk/dcmfg/concatenationloader.h
+           dcmfg/libsrc/concatenationloader.cc
+           dcmfg/tests/t_concatenation_loader.cc
+
+**** Changes from 2020.04.22 (eichelberg)
+
+- Fixed memory leak in DcmFindSCU::performQuery():
+  Fixed memory leak in DcmFindSCU::performQuery() caused by an
+  T_ASC_Association structure not being deleted when association
+  negotiation has failed.
+  Thanks to Matthias Gierlings <matthias.gierlings@ruhr-uni-bochum.de>
+  for the bug report.
+  Affects: dcmnet/libsrc/dfindscu.cc
+
+**** Changes from 2020.04.17 (riesmeier)
+
+- Use DIMSE-C message specific status codes:
+  Use DIMSE Status Codes that are specific to the respective message type,
+  e.g. C-FIND, C-GET, C-MOVE and C-STORE, where appropriate.
+  This closes DCMTK Conformance #598.
+  Affects: dcmnet/include/dcmtk/dcmnet/dimse.h
+           dcmnet/libsrc/dimdump.cc
+           dcmnet/libsrc/dimfind.cc
+           dcmnet/libsrc/dimget.cc
+           dcmnet/libsrc/dimmove.cc
+           dcmnet/libsrc/dimstore.cc
+           dcmnet/tests/tscusession.cc
+
+- Added comment on "convert" parameter (Windows):
+  Added missing comment to the API documentation of the constructor that the
+  "convert" parameter only works on Windows systems.
+  Affects: ofstd/include/dcmtk/ofstd/offile.h
+
+**** Changes from 2020.04.11 (eichelberg)
+
+- Fixed warnings on Sun Studio 12.6:
+  Renamed two methods to avoid warnings on Sun Studio 12.6.
+  Affects: dcmsign/include/dcmtk/dcmsign/sitsfs.h
+           dcmsign/libsrc/dcsighlp.cc
+           dcmsign/libsrc/sitsfs.cc
+
+**** Changes from 2020.04.10 (eichelberg)
+
+- Fixed dcmtls unit tests:
+  Fixed dcmtls unit tests in cases where OpenSSL support is disabled.
+  This also fixes the linker error related to libwrap on NetBSD.
+  Affects: dcmtls/tests/tests.cc
+           dcmtls/tests/tscuscptls.cc
+
+- Cleanup of the TLS support for DcmSCP and DcmSCPPool.
+  Affects: dcmnet/apps/dcmrecv.cc
+           dcmnet/include/dcmtk/dcmnet/scpcfg.h
+           dcmnet/libsrc/scp.cc
+           dcmnet/libsrc/scpcfg.cc
+           dcmnet/libsrc/scppool.cc
+
+**** Changes from 2020.04.09 (riesmeier)
+
+- Fixed various issues with new TLS support:
+  Made sure that the tool compiles without OpenSSL and when configured with
+  GNU Autioconf. Also fixed various other (minor) issues.
+  Affects: dcmnet/apps/Makefile.in
+           dcmnet/apps/dcmrecv.cc
+
+**** Changes from 2020.04.09 (eichelberg)
+
+- Replaced strncpy() with OFStandard::strlcpy():
+  Replaced code that used strncpy() and manually managed the trailing zero
+  byte with calls to OFStandard::strlcpy(). This fixes a couple of warnings
+  reported by gcc -Wstringop-truncation.
+  Affects: dcmnet/libsrc/assoc.cc
+
+- Fixed minor warnings:
+  Fixed minor warnings reported by gcc -Wshadow.
+  Affects: dcmwlm/libsrc/wlfsim.cc
+
+- Added TLS support to dcmrecv:
+  Added TLS support to the DcmSCP based dcmrecv command line tool.
+  Affects: dcmnet/apps/CMakeLists.txt
+           dcmnet/apps/dcmrecv.cc
+           dcmnet/docs/dcmrecv.man
+
+- Added TLS support to DcmSCP and DcmSCPPool:
+  Added support for Transport Layer Security functionality to the DcmSCP
+  and DcmSCPPool classes.
+  Thanks to Michel Amat (github user amatm) and Damien Lerat for the
+  implementation and pull request.
+  Added:   dcmtls/tests/CMakeLists.txt
+           dcmtls/tests/tests.cc
+           dcmtls/tests/tscuscptls.cc
+  Affects: dcmnet/include/dcmtk/dcmnet/scpcfg.h
+           dcmnet/libsrc/scp.cc
+           dcmnet/libsrc/scpcfg.cc
+           dcmnet/libsrc/scppool.cc
+           dcmtls/CMakeLists.txt
+
+**** Changes from 2020.04.07 (eichelberg)
+
+- Fixed Derivation Code Sequence creation:
+  The dcmjpeg encoder does not anymore create a derivation code sequence
+  when lossless compression is performed.
+  Thanks to Markus Sabin <Markus.Sabin@soft-gate.de> for the bug report
+  and patch.
+  This closes DCMTK issue #924.
+  Affects: dcmjpeg/libsrc/djcodece.cc
+
+**** Changes from 2020.04.06 (onken)
+
+- Try to fix VS 2008/2010 build.
+  Affects: dcmfg/libsrc/concatenationloader.cc
+
+**** Changes from 2020.04.03 (arizpegomez)
+
+- Added Encapsulated Document Length (CP 1851):
+  Included optional attribute Encapsulated Document Length to dcencdoc.cc
+  This closed DCMTK Conformance #877.
+  Affects: dcmdata/libsrc/dcencdoc.cc
+
+- Line spacing minor changes.
+  Affects: dcmdata/libsrc/dcencdoc.cc
+
+**** Changes from 2020.04.01 (riesmeier)
+
+- Updated and revised DIMSE Status Code definitions:
+  Updated and completely revised DIMSE Status Code definitions. Now, the
+  definitions and also the log output are consistent with the current
+  edition of the DICOM standard. Some Service Class specific DIMSE-N
+  Status Codes that are not needed for the DCMTK are still missing and
+  will be added in a future commit.
+  This closes DCMTK Conformance #803 and partly closes Conformance #598.
+  Affects: dcmdata/include/dcmtk/dcmdata/dcuid.h
+           dcmnet/include/dcmtk/dcmnet/dimse.h
+           dcmnet/libsrc/dimdump.cc
+           dcmnet/tests/tdimse.cc
+
+**** Changes from 2020.03.25 (riesmeier)
+
+- Added missing VRs "OL" and "OV" to documentation.
+  Affects: dcmdata/docs/dcm2json.man
+
+- Added missing VR "OL" to documentation.
+  Affects: dcmdata/docs/dcm2xml.man
+
+**** Changes from 2020.03.19 (riesmeier)
+
+- Fixed two typos in API documentation:
+  Thanks to GitHub user "Raphexion" (Niklas Johansson) for the patch.
+  Affects: dcmpstat/include/dcmtk/dcmpstat/dvpstx.h
+
+**** Changes from 2020.03.15 (eichelberg)
+
+- Various fixes to the dcmqrscp.cfg parser:
+  Thanks to Jake Cobb <Jake.Cobb@varian.com> for the bug report and patch.
+  Affects: dcmqrdb/libsrc/dcmqrcnf.cc
+
+- Fixed compilation with LibreSSL on OpenBSD 6.6.
+  Affects: dcmsign/libsrc/sitstamp.cc
+
+**** Changes from 2020.03.06 (riesmeier)
+
+- Added new file missing for previous commit.
+  Added:   dcmnet/tests/tdimse.cc
+  Affects: dcmnet/tests/tdump.cc
+
+- Added macros for further DIMSE Status Classes:
+  Added further macros to check for certain DIMSE Status Classes (e.g.
+  failure). Also added macro that checks whether a DIMSE Status Code is
+  valid, i.e. within the range defined by the DICOM standard (see PS3.7
+  Annext C).
+  Furthermore, all these new (and old) macros are tested in a new test case.
+  This partly closes DCMTK Conformance #803.
+  Affects: dcmnet/include/dcmtk/dcmnet/dimse.h
+           dcmnet/tests/CMakeLists.txt
+           dcmnet/tests/Makefile.in
+           dcmnet/tests/tdump.cc
+           dcmnet/tests/tests.cc
+
+- Fixed definition of DICOM_PENDING_STATUS macro:
+  According to DICOM PS3.7 Annex C, the "Pending" Status Class is defined as
+  Status Code "FF00 and FF01" (and not as "FFxx").
+  Affects: dcmnet/include/dcmtk/dcmnet/dimse.h
+
+- Added missing code to DICOM_WARNING_STATUS macro:
+  Added missing DIMSE Status Code "0001" to the DICOM_WARNING_STATUS macro
+  (see PS3.7 Annex C).
+  Affects: dcmnet/include/dcmtk/dcmnet/dimse.h
+
+**** Changes from 2020.03.05 (riesmeier)
+
+- Fixed issues with previous commit:
+  Instead of "@DCMTK_CMAKE_BUILD_TYPE@" "@CMAKE_BUILD_TYPE@" should be used.
+  Also fixed typo in CMake variable name ("DCMTK_CMAKE_INSTALL_INLCUDEDIR")
+  and added missing "DCMTK_CMAKE_INSTALL_SYSCONFDIR".
+  Affects: CMake/DCMTKConfig.cmake.in
+
+**** Changes from 2020.03.03 (onken)
+
+- Export more build options to DCMTKConfig.cmake.
+  Affects: CMake/DCMTKConfig.cmake.in
+
+**** Changes from 2020.03.02 (eichelberg)
+
+- DCMTK now compiles when UNICODE/_UNICODE is defined:
+  DCMTK will now successfully compile when the UNICODE and _UNICODE macros
+  are defined on Windows. We now explicitly call the Windows API functions
+  that are not remapped to wide-char versions depending on the presence of
+  the UNICODE defines.
+  This closes DCMTK issue #425.
+  Affects: INSTALL
+           dcmdata/libsrc/dcencdoc.cc
+           dcmdata/libsrc/dcuid.cc
+           dcmnet/apps/storescp.cc
+           dcmnet/libsrc/dul.cc
+           dcmpstat/apps/dcmprscu.cc
+           dcmpstat/apps/dcmpsrcv.cc
+           dcmpstat/libsrc/dviface.cc
+           oflog/include/dcmtk/oflog/clogger.h
+           oflog/include/dcmtk/oflog/config.h
+           oflog/include/dcmtk/oflog/configrt.h
+           oflog/include/dcmtk/oflog/fstreams.h
+           oflog/include/dcmtk/oflog/helpers/property.h
+           oflog/include/dcmtk/oflog/socketap.h
+           oflog/include/dcmtk/oflog/streams.h
+           oflog/include/dcmtk/oflog/tchar.h
+           oflog/include/dcmtk/oflog/tstring.h
+           oflog/libsrc/config.cc
+           oflog/libsrc/env.cc
+           oflog/libsrc/fileap.cc
+           oflog/libsrc/fileinfo.cc
+           oflog/libsrc/globinit.cc
+           oflog/libsrc/log4judp.cc
+           oflog/libsrc/ntelogap.cc
+           oflog/libsrc/property.cc
+           oflog/libsrc/snprintf.cc
+           oflog/libsrc/sockbuff.cc
+           oflog/libsrc/socketap.cc
+           oflog/libsrc/strhelp.cc
+           oflog/libsrc/timehelp.cc
+           oflog/libsrc/winconap.cc
+           oflog/libsrc/windebap.cc
+           oflog/libsrc/winsock.cc
+           ofstd/include/dcmtk/ofstd/ofxml.h
+           ofstd/libsrc/ofstd.cc
+           ofstd/libsrc/oftempf.cc
+           ofstd/tests/tests.cc
+           ofstd/tests/txml.cc
+
+**** Changes from 2020.02.26 (eichelberg)
+
+- Fixed previous commit, which was incomplete.
+  Affects: dcmqrdb/include/dcmtk/dcmqrdb/dcmqrcbf.h
+           dcmqrdb/include/dcmtk/dcmqrdb/dcmqrcnf.h
+           dcmqrdb/include/dcmtk/dcmqrdb/dcmqrdba.h
+
+- Fixed inconsistent forward declaration:
+  Fixed declaration of DcmQueryRetrieveCharacterSetOptions, which was declared
+  as a class in one place and as a struct in another place.
+  Thanks to Waldo Valenzuela <waldo.valenzuela@artorg.unibe.ch> for the bug report.
+  Affects: dcmqrdb/include/dcmtk/dcmqrdb/dcmqrdba.h
+
+**** Changes from 2020.02.25 (eichelberg)
+
+- Improved CMake options for the WIN32 build model:
+  When compiling on windows, two CMake options can now be used to control the
+  Win32 build model (multithreaded or multithreaded DLL). When
+  DCMTK_OVERWRITE_WIN32_COMPILER_FLAGS is ON, the build model can be selected
+  by setting DCMTK_COMPILE_WIN32_MULTITHREADED_DLL (ON for multithreaded DLL,
+  OFF for multithreaded). When DCMTK_OVERWRITE_WIN32_COMPILER_FLAGS is OFF,
+  the DCMTK_COMPILE_WIN32_MULTITHREADED_DLL option is ignored and CMake's
+  default compiler options are used.
+  This closes DCMTK issue #903.
+  Affects: CMake/DCMTKConfig.cmake.in
+           CMake/dcmtkPrepare.cmake
+           INSTALL
+
+**** Changes from 2020.02.24 (riesmeier)
+
+- Added option --socket-timeout to findscu:
+  Added option --socket-timeout to findscu (as already done for e.g. storescu
+  or echoscu). Also changed the way default values of command line options are
+  specified (now using the same approach as for other similar tools).
+  This partly closed DCMTK Feature #711.
+  Affects: dcmnet/apps/findscu.cc
+           dcmnet/docs/findscu.man
+
+**** Changes from 2020.02.21 (eichelberg)
+
+- Increased buffer size to fix gcc 9.2 warning.
+  Affects: dcmsign/libsrc/dcsighlp.cc
+
+**** Changes from 2020.02.18 (riesmeier)
+
+- Removed escaping of "\" in Doxygen documentation.
+  Affects: dcmdata/docs/dcm2xml.man
+           dcmdata/docs/xml2dcm.man
+
+- Added new VRs UV, SV and OV to the documentation:
+  Also fixed other minor issues in the documentation of this tool.
+  Affects: dcmdata/apps/dump2dcm.cc
+           dcmdata/docs/dump2dcm.man
+
+**** Changes from 2020.02.14 (riesmeier)
+
+- Added support for new Storage SOP Classes:
+  Added definition of new Storage SOP Class UIDs from Supplement 176 (Second
+  Generation Radiotherapy - Tomotherapeutic and Robotic-Arm Treatment
+  Modalities) and Supplement 208 (DICOM Encapsulation of OBJ Models for 3D
+  Manufacturing and Virtual Reality).
+  This commit also adds support for the various networking tools and for
+  generating a DICOMDIR referencing objects of the underlying IODs.
+  Affects: dcmdata/include/dcmtk/dcmdata/dcuid.h
+           dcmdata/libsrc/dcddirif.cc
+           dcmdata/libsrc/dcuid.cc
+           dcmnet/docs/movescu.man
+           dcmnet/docs/storescp.man
+           dcmnet/etc/storescp.cfg
+           dcmnet/etc/storescu.cfg
+           dcmqrdb/docs/dcmqrscp.man
+           dcmqrdb/etc/dcmqrprf.cfg
+
+- Added new well-known Frame of Reference UID:
+  Added well-known Frame of Reference UID from Supplement 176 (Second Generation
+  Radiotherapy - Tomotherapeutic and Robotic-Arm Treatment Modalities).
+  Affects: dcmdata/include/dcmtk/dcmdata/dcuid.h
+           dcmdata/libsrc/dcuid.cc
+
+**** Changes from 2020.02.13 (riesmeier)
+
+- Fixed issue with order of include directories:
+  Fixed issue with order of include directories when working with CMake on
+  a system where the DCMTK libraries and header files are already installed
+  in the same directory as one of the external support libraries (e.g. zlib
+  or libiconv in "/usr/local").
+  Thanks to Steve Pieper <pieper@isomics.com> for the original report and
+  the in-depth analysis.
+  Affects: CMakeLists.txt
+
+**** Changes from 2020.02.07 (riesmeier)
+
+- Output error reason to logger:
+  Always output the reason (e.g. called function) for an error to the logger,
+  not only the value of the OFCondition variable.
+  Also removed redundant information in case of "bad override key/path".
+  Affects: dcmnet/libsrc/dfindscu.cc
+
+**** Changes from 2020.02.04 (riesmeier)
+
+- Updated Context Group classes for DICOM 2020a:
+  Updated automatically generated Context Group classes for the 2020a edition
+  of the DICOM standard. All supported classes were updated, even though there
+  were no changes to most of them.
+  Affects: dcmsr/include/dcmtk/dcmsr/cmr/cid100.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid10013.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid10033.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid11.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid244.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid29.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4020.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4021.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4031.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid42.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid6147.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7021.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7181.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7445.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7452.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7453.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7464.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7469.h
+           dcmsr/libcmr/cid100.cc
+           dcmsr/libcmr/cid10013.cc
+           dcmsr/libcmr/cid10033.cc
+           dcmsr/libcmr/cid11.cc
+           dcmsr/libcmr/cid244.cc
+           dcmsr/libcmr/cid29.cc
+           dcmsr/libcmr/cid4020.cc
+           dcmsr/libcmr/cid4021.cc
+           dcmsr/libcmr/cid4031.cc
+           dcmsr/libcmr/cid42.cc
+           dcmsr/libcmr/cid6147.cc
+           dcmsr/libcmr/cid7021.cc
+           dcmsr/libcmr/cid7181.cc
+           dcmsr/libcmr/cid7445.cc
+           dcmsr/libcmr/cid7452.cc
+           dcmsr/libcmr/cid7453.cc
+           dcmsr/libcmr/cid7464.cc
+           dcmsr/libcmr/cid7469.cc
+
+- Updated code definitions for DICOM 2020a:
+  Updated automatically generated code definitions for coding scheme "DCM"
+  and "NCIt". For the coding scheme "UMLS", there were no changes.
+  Affects: dcmsr/include/dcmtk/dcmsr/codes/dcm.h
+           dcmsr/include/dcmtk/dcmsr/codes/ncit.h
+           dcmsr/include/dcmtk/dcmsr/codes/umls.h
+
+**** Changes from 2020.01.31 (riesmeier)
+
+- Updated data dictionary for DICOM 2020a:
+  Updated data dictionary for the latest edition of the DICOM standard.
+  Affects: dcmdata/data/dicom.dic
+           dcmdata/include/dcmtk/dcmdata/dcdeftag.h
+           dcmdata/libsrc/dcdictbi.cc
+
+- Made use of new internal VR "px" for pixel data:
+  Now using the new internal VR "px" for the standard Pixel Data attribute
+  (7fe0,0010) as well as for the private attribute (7fe1,1060), which is
+  created by GE Vivid S70 ultrasound systems in a non-standard conformant
+  manner (also for compressed pixel data, i.e. in encapsulated format).
+  Thanks to Marcel Claus <Marcel.Claus@med.uni-jena.de> for the report and
+  for providing sample objects of the GE Vivid S70.
+  Affects: dcmdata/data/dicom.dic
+           dcmdata/data/private.dic
+           dcmdata/include/dcmtk/dcmdata/dcdeftag.h
+           dcmdata/libsrc/dcdictbi.cc
+
+- Introduced new internal VR "px" for pixel data:
+  Introduced new internal value representation "px" that can be used for pixel
+  data, both uncompressed (OB or OW) and compressed (pixel sequence). This new
+  type allows for treating other attributes than (7fe0,0010) in the same way as
+  the Pixel Data attribute, by simply specifying the tag in the data dictionary.
+  In a subsequent commit, this new feature will be used for the standard Pixel
+  Data attribute but also for private ones.
+  Affects: dcmdata/apps/dump2dcm.cc
+           dcmdata/apps/xml2dcm.cc
+           dcmdata/include/dcmtk/dcmdata/dcvr.h
+           dcmdata/libsrc/dcitem.cc
+           dcmdata/libsrc/dcpixel.cc
+           dcmdata/libsrc/dcvr.cc
+           dcmdata/libsrc/dcvrpobw.cc
+           dcmdata/tests/telemlen.cc
+           dcmdata/tests/tests.cc
+           dcmpstat/libsrc/dvpscu.cc
+
+**** Changes from 2020.01.24 (onken)
+
+- Enhanced documentation.
+  Affects: dcmdata/include/dcmtk/dcmdata/libi2d/i2d.h
+
+**** Changes from 2020.01.23 (riesmeier)
+
+- Added SOP class UIDs from Supplement 202:
+  Added definition of four new SOP class UIDs introduced with Supplement 202
+  (Real-Time Video).
+  This closed DCMTK Conformance #898.
+  Affects: dcmdata/include/dcmtk/dcmdata/dcuid.h
+           dcmdata/libsrc/dcuid.cc
+
+- Added transfer syntax UIDs from Supplement 202:
+  Added definition of transfer syntax UIDs from Supplement 202 (Real-Time
+  Video). The class DcmXfer has not been extended accordingly since the
+  three new transfer syntaxes (2 for video and 1 for audio) are only used
+  for the new "DICOM-RTV" service and not for encoding a DICOM dataset.
+  This partly closed DCMTK Conformance #898.
+  Affects: dcmdata/include/dcmtk/dcmdata/dcuid.h
+           dcmdata/libsrc/dcuid.cc
+
+**** Changes from 2020.01.22 (onken)
+
+- Fixed typo in INSTALL file:
+  Thanks to GitHub user "iboB" for the report and fix.
+  Affects: INSTALL
+
+**** Changes from 2020.01.17 (riesmeier)
+
+- Fixed inappropriate warning on invalid frame time:
+  There are rare cases, where a frame time of 0 make sense, e.g. if the Cine
+  Module is required for single frame images (see PS3.3 Section C.7.6.6.1.2).
+  Affects: dcmimgle/libsrc/diimage.cc
+
+**** Changes from 2020.01.08 (riesmeier)
+
+- Various fixes to formatting and documentation:
+  Various fixes to source code formatting and Doxygen documentation of the
+  manpage (e.g. missing command line options and missing Doxygen markup).
+  Affects: dcmsign/apps/dcmsign.cc
+           dcmsign/docs/dcmsign.man
+
+**** Changes from 2020.01.07 (eichelberg)
+
+- Added --convert-un option to dcmsign.
+  Affects: dcmsign/apps/dcmsign.cc
+           dcmsign/docs/dcmsign.man
+
+**** Changes from 2020.01.06 (onken)
+
+- Use typedef instead of #define for OFBool.
+  Affects: ofstd/include/dcmtk/ofstd/oftypes.h
+
+**** Changes from 2020.01.05 (riesmeier)
+
+- Made sure appropriate data dictionary is used:
+  Made sure that an appropriate DICOM data dictionary is used when performing
+  the test cases using "make check" (GNU Autoconf).
+  Affects: dcmiod/tests/Makefile.in
+
+- Increased buffer size for use of sprintf():
+  Increased buffer size for use of sprintf() in order to avoid possible buffer
+  overflow reported by gcc 9.2.1 with option -Wformat-overflow, which is enabled
+  by default on Ubuntu 19.10 Linux.
+  Affects: dcmpstat/libsrc/dviface.cc
+           dcmpstat/libsrc/dvsighdl.cc
+
+- Minor fixes to source code formatting:
+  Fixed source code formatting (for reasons of consistency with the rest
+  of the file).
+  Affects: dcmnet/apps/storescp.cc
+
+**** Changes from 2020.01.05 (eichelberg)
+
+- Fixed bug in the parsing of UN VR sequences:
+  Added command line option --convert-un to storescp and fixed a bug in the
+  parser that caused parse errors when receiving a large sequence element with
+  explicit length and UN value representation, while --convert-un is active.
+  Thanks to Jesper Bojesen <jbojesen@vitalimages.com> for the bug report and fix.
+  This closes DCMTK issue #888.
+  Affects: dcmdata/libsrc/dcitem.cc
+           dcmnet/apps/storescp.cc
+           dcmnet/docs/storescp.man
+
+**** Changes from 2020.01.02 (riesmeier)
+
+- Made sure appropriate data dictionary is used:
+  Made sure that an appropriate DICOM data dictionary is used when performing
+  the test cases using "make check" (GNU Autoconf).
+  Affects: dcmect/tests/Makefile.in
+           dcmfg/tests/Makefile.in
+           dcmseg/tests/Makefile.in
+
+**** Changes from 2020.01.02 (onken)
+
+- Force OFBool mapping to system bool type:
+  Drops support for systems that do not natively support the bool type.
+  Affects: CMake/GenerateDCMTKConfigure.cmake
+           CMake/osconfig.h.in
+           config/aclocal.m4
+           config/configure
+           config/configure.in
+           config/confmod
+           config/include/dcmtk/config/osconfig.h.in
+           ofstd/include/dcmtk/ofstd/oflimits.h
+           ofstd/include/dcmtk/ofstd/oftraits.h
+           ofstd/include/dcmtk/ofstd/oftypes.h
+           ofstd/libsrc/Makefile.dep
+
+- Renamed method for consistency.
+  Affects: dcmdata/include/dcmtk/dcmdata/dcbytstr.h
+           dcmdata/libsrc/dcbytstr.cc
+           dcmdata/libsrc/dcvrds.cc
+
+- Updated autoconf dependencies.
+  Affects: dcmiod/tests/Makefile.dep
+           dcmnet/apps/Makefile.dep
+           dcmnet/libsrc/Makefile.dep
+           dcmnet/tests/Makefile.dep
+           dcmpstat/libsrc/Makefile.dep
+           dcmsign/apps/Makefile.dep
+           dcmsign/libsrc/Makefile.dep
+           dcmtls/libsrc/Makefile.dep
+
+- Use consistent C-FIND/GET/MOVE status codes:
+  DcmSCU now uses status code strings that have already been defined in
+  dimdump.cc in order to use consistent status strings throughout the
+  toolkit.
+  Refactored C-FIND/GET/MOVE default session handling in DcmSCU to benefit
+  from common code.
+  Added (simple, for now) test for C-FIND/MOVE session handling.
+  Added:   dcmnet/tests/tscusession.cc
+  Affects: dcmnet/include/dcmtk/dcmnet/scu.h
+           dcmnet/libsrc/scu.cc
+           dcmnet/tests/CMakeLists.txt
+           dcmnet/tests/Makefile.in
+           dcmnet/tests/tests.cc
+
+**** Changes from 2019.12.31 (eichelberg)
+
+- Fixed minor bug.
+  Affects: dcmsign/libsrc/dcsignat.cc
+
+**** Changes from 2019.12.30 (eichelberg)
+
+- Added support for OpenSSL without Elliptic Curves:
+  Added support for OpenSSL libraries compiled without support for Elliptic
+  Curves. Needed for compiling DCMTK with the OpenSSL library shipped with
+  Solaris 11.3.
+  Affects: dcmsign/apps/dcmsign.cc
+           dcmsign/include/dcmtk/dcmsign/sitypes.h
+           dcmsign/libsrc/sicert.cc
+           dcmsign/libsrc/siecdsa.cc
+           dcmsign/libsrc/siprivat.cc
+           dcmsign/libsrc/sitypes.cc
+
+**** Changes from 2019.12.30 (onken)
+
+- Fixed tag type for long code value support:
+  Make sure Code Value, Long Code Value and URN Code Value are all of type
+  1C now. Fixes CP 1031 support introduced in recent commit a7ca3a60.
+  Affects: dcmiod/libsrc/iodmacro.cc
+
+- Minor formatting enhancements.
+  Affects: dcmiod/include/dcmtk/dcmiod/modusfor.h
+           dcmiod/libsrc/iodutil.cc
+           dcmiod/libsrc/modfloatingpointimagepixel.cc
+
+- Added support for long code values (CP 1301).
+  Added:   dcmiod/tests/tcodes.cc
+  Affects: dcmiod/include/dcmtk/dcmiod/iodmacro.h
+           dcmiod/libsrc/iodmacro.cc
+           dcmiod/tests/CMakeLists.txt
+           dcmiod/tests/Makefile.in
+           dcmiod/tests/tests.cc
+
+- Fixed compiler warnings (VS 2019).
+  Affects: dcmect/tests/t_huge_concat.cc
+           dcmect/tests/t_roundtrip.cc
+           dcmseg/tests/troundtrip.cc
+
+**** Changes from 2019.12.29 (eichelberg)
+
+- Compatibility fixes for OpenSSL 1.0.1:
+  The revised dcmsign module now also compiles and works with OpenSSL 1.0.1,
+  the oldest OpenSSL version still supported in DCMTK. This required a rewrite
+  of the date/time comparison code since ASN1_TIME_diff() is not available
+  in OpenSSL 1.0.1.
+  Affects: dcmsign/include/dcmtk/dcmsign/sicert.h
+           dcmsign/libsrc/sicert.cc
+           dcmsign/libsrc/sitstamp.cc
+
+**** Changes from 2019.12.28 (eichelberg)
+
+- Fixed some minor warnings reported by VS2019.
+  Affects: dcmsign/libsrc/sitstamp.cc
+
+- Compatibility fixes for OpenSSL 1.0.2 and MSVC.
+  Affects: dcmsign/apps/dcmsign.cc
+           dcmsign/include/dcmtk/dcmsign/sitypes.h
+           dcmsign/libsrc/dcsighlp.cc
+           dcmsign/libsrc/dcsignat.cc
+           dcmsign/libsrc/sicert.cc
+           dcmsign/libsrc/siecdsa.cc
+           dcmsign/libsrc/sitstamp.cc
+
+**** Changes from 2019.12.27 (eichelberg)
+
+- Major revision of dcmsign module:
+  This commit completes a major revision of the dcmsign module, which adds the
+  following features:
+  - support for Elliptic Curve (ECDSA) signatures,
+  - support for the DICOM SR RSA Digital Signature Profile,
+  - support for CRLs in hashed certificate directories,
+  - verify chain of trust for signer certificates during signature verification,
+  - support for the verification of trusted timestamps,
+  - limited support for the creation of trusted timestamps: a timestamp
+    query can be generated during the signature process, but no support for the
+    network protocols defined in RFC 3161 is implemented yet,
+  - many bug fixes, improved error handling and logging.
+  Affects: dcmsign/docs/dcmsign.dox
+
+- Various improvements to dcmsign module:
+  Signature creation now fails with an error message if one of the tags
+  specified with --tag or --tag-file are not present in the dataset to
+  be signed. Furthermore, the digital signature purpose code is now printed
+  during signature verification. The 64kByte size limit for --tag-file
+  has been removed.
+  Affects: dcmsign/docs/dcmsign.man
+           dcmsign/include/dcmtk/dcmsign/dcsignat.h
+           dcmsign/libsrc/dcsighlp.cc
+           dcmsign/libsrc/dcsignat.cc
+
+- Improved timestamp verification code:
+  The timestamp verification code now performs additional consistency
+  checks (for example whether the timestamp was created before the start
+  of validity of the TSA certificate). Furthermore, a valid certified
+  timestamp can now extend the "lifetime" of a signature where the
+  signer certificate has expired, if the timestamp is still valid.
+  Affects: dcmsign/include/dcmtk/dcmsign/sicertvf.h
+           dcmsign/include/dcmtk/dcmsign/sitstamp.h
+           dcmsign/libsrc/dcsighlp.cc
+           dcmsign/libsrc/sicertvf.cc
+           dcmsign/libsrc/sitstamp.cc
+
+- Improved handling of CRLs and unsignable attributes:
+  Improved implementation of certificate revocation lists, which can now
+  also be stored in a hashed certificate directory. Improved handling and
+  error reporting related to unsignable attributes (such as group lengths
+  or UN attributes) present during signature creation of verification.
+  Affects: dcmsign/apps/dcmsign.cc
+           dcmsign/docs/dcmsign.man
+           dcmsign/include/dcmtk/dcmsign/sicertvf.h
+           dcmsign/include/dcmtk/dcmsign/simaccon.h
+           dcmsign/include/dcmtk/dcmsign/sisprof.h
+           dcmsign/include/dcmtk/dcmsign/sitypes.h
+           dcmsign/libsrc/dcsignat.cc
+           dcmsign/libsrc/sicertvf.cc
+           dcmsign/libsrc/simaccon.cc
+           dcmsign/libsrc/sisprof.cc
+           dcmsign/libsrc/sitypes.cc
+
+- Check unconditional attributes in signature profiles:
+  Signature verification now checks whether all attributes unconditionally
+  required to be signed are included in the signature when verifying
+  signatures against a signature profile.
+  Affects: dcmsign/include/dcmtk/dcmsign/siautopr.h
+           dcmsign/include/dcmtk/dcmsign/sibrsapr.h
+           dcmsign/include/dcmtk/dcmsign/sicreapr.h
+           dcmsign/include/dcmtk/dcmsign/sinullpr.h
+           dcmsign/include/dcmtk/dcmsign/sisprof.h
+           dcmsign/include/dcmtk/dcmsign/sisrpr.h
+           dcmsign/include/dcmtk/dcmsign/sisrvpr.h
+           dcmsign/libsrc/dcsighlp.cc
+           dcmsign/libsrc/dcsignat.cc
+           dcmsign/libsrc/siautopr.cc
+           dcmsign/libsrc/sibrsapr.cc
+           dcmsign/libsrc/sicreapr.cc
+           dcmsign/libsrc/sinullpr.cc
+           dcmsign/libsrc/sisprof.cc
+           dcmsign/libsrc/sisrpr.cc
+           dcmsign/libsrc/sisrvpr.cc
+
+- Fixed bug affecting multiple nested signatures:
+  Fixed bug that caused digital signatures embedded in a sequence item to be
+  included in the bitstream of another sequence (e.g. on main dataset level)
+  that signed the sequence containing this sequence item. In this case the
+  bitstream generated for the signature creation or verification was
+  not DICOM compliant.
+  Affects: dcmdata/libsrc/dcitem.cc
+
+- Check if cert was valid during signature creation:
+  When verifying signatures, dcmsign now checks whether the signature datetime
+  is within the validity period of the signer certificate.
+  Affects: dcmsign/apps/dcmsign.cc
+           dcmsign/docs/dcmsign.man
+           dcmsign/include/dcmtk/dcmsign/dcsignat.h
+           dcmsign/include/dcmtk/dcmsign/sicert.h
+           dcmsign/include/dcmtk/dcmsign/sitypes.h
+           dcmsign/libsrc/dcsignat.cc
+           dcmsign/libsrc/sicert.cc
+           dcmsign/libsrc/sitypes.cc
+
+- Print error message when signature is incomplete:
+  dcmsign now prints an error message when any of the required attributes of
+  the MACParametersSequence or the DigitalSignaturesSequence are absent,
+  empty or invalid, instead of silently ignoring such invalid signatures.
+  Affects: dcmsign/include/dcmtk/dcmsign/dcsignat.h
+           dcmsign/libsrc/dcsignat.cc
+           dcmsign/libsrc/sicert.cc
+
+- Fixed warnings reported by gcc -Wshadow.
+  Affects: dcmqrdb/libsrc/dcmqrdbi.cc
+
+- Print warning to logger when encountering weak key:
+  Print a warning to the logger when a weak key (RSA/DSA < 1024 bits or
+  ECDSA < 256 bits) is encountered in a certificate during signature
+  creation or verification.
+  Affects: dcmsign/include/dcmtk/dcmsign/sicert.h
+           dcmsign/libsrc/dcsighlp.cc
+           dcmsign/libsrc/dcsignat.cc
+           dcmsign/libsrc/sicert.cc
+
+- Correctly print EC curve bits.
+  Affects: dcmpstat/libsrc/dvsighdl.cc
+
+- Implemented well-defined exit codes for dcmsign.
+  Affects: dcmsign/apps/dcmsign.cc
+           dcmsign/docs/dcmsign.man
+           dcmsign/libsrc/dcsighlp.cc
+
+- Fixed memory leak in class SiCertificate.
+  Affects: dcmsign/libsrc/sicert.cc
+
+- Revised signature verification code:
+  Revised the signature verification code, which now checks the validity of the
+  signer's certificate by checking the chain of trust. Furthermore, the user can
+  now verify if any of the signatures present are a valid creator, authorization
+  or SR RSA signature. Also implemented support for adding certified timestamps
+  from a RFC 3161 Timestamp Response (TSR) file. When verifying a signature,
+  certified timestamps will now also be discovered and verified.
+  Added:   dcmsign/include/dcmtk/dcmsign/sitsfs.h
+           dcmsign/libsrc/sitsfs.cc
+           dcmsign/libsrc/sitstamp.cc
+  Affects: dcmqrdb/include/dcmtk/dcmqrdb/dcmqrcbf.h
+           dcmqrdb/libsrc/dcmqrcnf.cc
+           dcmsign/apps/dcmsign.cc
+           dcmsign/docs/dcmsign.man
+           dcmsign/include/dcmtk/dcmsign/dcsighlp.h
+           dcmsign/include/dcmtk/dcmsign/dcsignat.h
+           dcmsign/include/dcmtk/dcmsign/siautopr.h
+           dcmsign/include/dcmtk/dcmsign/sibrsapr.h
+           dcmsign/include/dcmtk/dcmsign/sicert.h
+           dcmsign/include/dcmtk/dcmsign/sicertvf.h
+           dcmsign/include/dcmtk/dcmsign/sicreapr.h
+           dcmsign/include/dcmtk/dcmsign/sinullpr.h
+           dcmsign/include/dcmtk/dcmsign/sisprof.h
+           dcmsign/include/dcmtk/dcmsign/sisrpr.h
+           dcmsign/include/dcmtk/dcmsign/sitstamp.h
+           dcmsign/include/dcmtk/dcmsign/sitypes.h
+           dcmsign/libsrc/CMakeLists.txt
+           dcmsign/libsrc/Makefile.in
+           dcmsign/libsrc/dcsighlp.cc
+           dcmsign/libsrc/dcsignat.cc
+           dcmsign/libsrc/siautopr.cc
+           dcmsign/libsrc/sibrsapr.cc
+           dcmsign/libsrc/sicert.cc
+           dcmsign/libsrc/sicertvf.cc
+           dcmsign/libsrc/sicreapr.cc
+           dcmsign/libsrc/sinullpr.cc
+           dcmsign/libsrc/sipurpos.cc
+           dcmsign/libsrc/sisrpr.cc
+           dcmsign/libsrc/sisrvpr.cc
+           dcmsign/libsrc/sitypes.cc
+
+- Fixed DER sequence length computation.
+  Affects: dcmsign/libsrc/dcsignat.cc
+
+- return non-zero when signature verification fails:
+  The dcmsign command line tool now returns a non-zero return code when one
+  or more of the signatures in a file have failed signature verification.
+  Affects: dcmsign/libsrc/dcsighlp.cc
+
+- Added support for SR RSA Digital Signature Profile:
+  Added support for the Structured Reporting RSA Digital Signature Profile
+  and the Digital Signature Purpose Code Sequence. Updated all signature
+  profile classes to include all required attributes as defined in DICOM 2019c.
+  Added:   dcmsign/include/dcmtk/dcmsign/dcsighlp.h
+           dcmsign/include/dcmtk/dcmsign/sipurpos.h
+           dcmsign/include/dcmtk/dcmsign/sisrpr.h
+           dcmsign/include/dcmtk/dcmsign/sisrvpr.h
+           dcmsign/libsrc/dcsighlp.cc
+           dcmsign/libsrc/sipurpos.cc
+           dcmsign/libsrc/sisrpr.cc
+           dcmsign/libsrc/sisrvpr.cc
+  Affects: dcmsign/apps/dcmsign.cc
+           dcmsign/docs/dcmsign.man
+           dcmsign/include/dcmtk/dcmsign/dcsignat.h
+           dcmsign/include/dcmtk/dcmsign/sialgo.h
+           dcmsign/include/dcmtk/dcmsign/siautopr.h
+           dcmsign/include/dcmtk/dcmsign/sibrsapr.h
+           dcmsign/include/dcmtk/dcmsign/sicert.h
+           dcmsign/include/dcmtk/dcmsign/sicertvf.h
+           dcmsign/include/dcmtk/dcmsign/sicreapr.h
+           dcmsign/include/dcmtk/dcmsign/sidsa.h
+           dcmsign/include/dcmtk/dcmsign/siecdsa.h
+           dcmsign/include/dcmtk/dcmsign/simac.h
+           dcmsign/include/dcmtk/dcmsign/simaccon.h
+           dcmsign/include/dcmtk/dcmsign/simd5.h
+           dcmsign/include/dcmtk/dcmsign/sinullpr.h
+           dcmsign/include/dcmtk/dcmsign/siprivat.h
+           dcmsign/include/dcmtk/dcmsign/siripemd.h
+           dcmsign/include/dcmtk/dcmsign/sirsa.h
+           dcmsign/include/dcmtk/dcmsign/sisha1.h
+           dcmsign/include/dcmtk/dcmsign/sisprof.h
+           dcmsign/include/dcmtk/dcmsign/sitypes.h
+           dcmsign/libsrc/CMakeLists.txt
+           dcmsign/libsrc/Makefile.in
+           dcmsign/libsrc/dcsignat.cc
+           dcmsign/libsrc/siautopr.cc
+           dcmsign/libsrc/sibrsapr.cc
+           dcmsign/libsrc/sicreapr.cc
+           dcmsign/libsrc/sinullpr.cc
+           dcmsign/libsrc/sisprof.cc
+           dcmsign/libsrc/sitypes.cc
+
+- Fix verification of odd-length DSA/ECDSA signatures.
+  Affects: dcmsign/libsrc/dcsignat.cc
+
+- Added initial support for ECDSA signatures.
+  Added:   dcmsign/include/dcmtk/dcmsign/siecdsa.h
+           dcmsign/libsrc/siecdsa.cc
+  Affects: dcmsign/apps/dcmsign.cc
+           dcmsign/include/dcmtk/dcmsign/sicert.h
+           dcmsign/include/dcmtk/dcmsign/sitypes.h
+           dcmsign/libsrc/CMakeLists.txt
+           dcmsign/libsrc/Makefile.in
+           dcmsign/libsrc/sicert.cc
+           dcmsign/libsrc/siprivat.cc
+
+**** Changes from 2019.12.20 (eichelberg)
+
+- Forward trusted certificates to DcmTLSTransportLayer:
+  Class DcmTLSSCU did not trusted certificate files and directories set with
+  DcmTLSSCU::addTrustedCertFile() and DcmTLSSCU::addTrustedCertDir() to the
+  underlying DcmTLSTransportLayer instance. This fix was developed by
+  Michael Onken already in 2017, but apparently never committed.
+  Affects: dcmtls/libsrc/tlsscu.cc
+
+**** Changes from 2019.12.17 (onken)
+
+- Fixed compiler warning (shadowed variable).
+  Affects: dcmseg/tests/troundtrip.cc
+
+**** Changes from 2019.12.12 (onken)
+
+- Fix OFtuple-based compile error in VS 2008/2010:
+  Try to fix OFtuple-based compile error in VS 2008/2010, and address
+  compiler warning in SunPro Studio 12.6 about possible NULL pointer
+  reference.
+  Affects: dcmect/tests/t_huge_concat.cc
+           dcmfg/libsrc/concatenationloader.cc
+
+**** Changes from 2019.12.11 (riesmeier)
+
+- Fixed warning reported by gcc (-Wsign-compare).
+  Affects: ofstd/tests/tmap.cc
+
+**** Changes from 2019.12.11 (onken)
+
+- Fixed more compiler warnings.
+  Affects: dcmdata/libi2d/i2djpgs.cc
+           dcmfg/libsrc/concatenationloader.cc
+           dcmseg/libsrc/segdoc.cc
+           dcmtract/libsrc/trctrack.cc
+
+- Fixed compiler warning.
+  Affects: dcmfg/libsrc/fgbase.cc
+
+- Fixed/completed doxygen documentation.
+  Affects: dcmdata/include/dcmtk/dcmdata/dcvrds.h
+           dcmpmap/include/dcmtk/dcmpmap/dpmparametricmapiod.h
+           dcmtract/include/dcmtk/dcmtract/trcmeasurement.h
+           dcmtract/include/dcmtk/dcmtract/trcmodtractresults.h
+           dcmtract/include/dcmtk/dcmtract/trcstatistic.h
+           dcmtract/include/dcmtk/dcmtract/trctrack.h
+           dcmtract/include/dcmtk/dcmtract/trctrackset.h
+
+- Removed accidentially commited configure file.
+  Removed: configure
+
+- Use constants instead of magic numbers.
+  Affects: dcmfg/include/dcmtk/dcmfg/concatenationcreator.h
+           dcmfg/libsrc/concatenationcreator.cc
+
+- Fixed data types and compiler warnings:
+  Fixed data types used in Concatenation code (e.g. maximum number of
+  frames per instance, maximum number of concatenation instances).
+  Fixed compiler warnings, especially those from integer conversions.
+  Adapted documentation where necessary.
+  Affects: dcmect/libsrc/enhanced_ct.cc
+           dcmfg/include/dcmtk/dcmfg/concatenationcreator.h
+           dcmfg/include/dcmtk/dcmfg/concatenationloader.h
+           dcmfg/include/dcmtk/dcmfg/fgctadditionalxraysource.h
+           dcmfg/include/dcmtk/dcmfg/fgfracon.h
+           dcmfg/include/dcmtk/dcmfg/fgimagedatatype.h
+           dcmfg/include/dcmtk/dcmfg/fgpixmsr.h
+           dcmfg/libsrc/concatenationcreator.cc
+           dcmfg/libsrc/concatenationloader.cc
+           dcmfg/libsrc/fgbase.cc
+           dcmfg/libsrc/fgctadditionalxraysource.cc
+           dcmfg/libsrc/fgfracon.cc
+           dcmfg/libsrc/fgimagedatatype.cc
+           dcmfg/libsrc/fgpixmsr.cc
+           dcmiod/include/dcmtk/dcmiod/iodcontentitemmacro.h
+           dcmiod/include/dcmtk/dcmiod/modfloatingpointimagepixel.h
+           dcmiod/include/dcmtk/dcmiod/modimagepixel.h
+           dcmiod/include/dcmtk/dcmiod/modimagepixelbase.h
+           dcmiod/include/dcmtk/dcmiod/modimagepixelvariant.h
+           dcmiod/include/dcmtk/dcmiod/modusfor.h
+           dcmiod/libsrc/iodcontentitemmacro.cc
+           dcmiod/libsrc/iodutil.cc
+           dcmiod/libsrc/modfloatingpointimagepixel.cc
+           dcmiod/libsrc/modimagepixel.cc
+           dcmiod/libsrc/modimagepixelbase.cc
+           dcmiod/libsrc/modusfor.cc
+           ofstd/include/dcmtk/ofstd/oftest.h
+
+- Fix recusion (call base class version instead).
+  Affects: dcmect/include/dcmtk/dcmect/enhanced_ct.h
+
+- Fixed nested angle brackets and other formatting:
+  Fixed nested closing angle brackets ("> >") for templates that require a
+  space in C++03.
+  Made formatting more consistent.
+  Affects: dcmect/include/dcmtk/dcmect/enhanced_ct.h
+           dcmect/libsrc/enhanced_ct.cc
+           dcmect/tests/t_huge_concat.cc
+           dcmect/tests/t_roundtrip.cc
+           dcmfg/include/dcmtk/dcmfg/concatenationloader.h
+           dcmfg/libsrc/fgderimg.cc
+           dcmiod/include/dcmtk/dcmiod/iodimage.h
+           dcmiod/include/dcmtk/dcmiod/iodutil.h
+           dcmiod/libsrc/iodcommn.cc
+           dcmiod/libsrc/iodcontentitemmacro.cc
+           dcmiod/libsrc/iodmacro.cc
+           dcmiod/libsrc/iodreferences.cc
+           dcmiod/libsrc/iodrules.cc
+           dcmiod/libsrc/iodutil.cc
+           dcmiod/libsrc/modacquisitioncontext.cc
+           dcmiod/libsrc/modbase.cc
+           dcmiod/libsrc/modcommoninstanceref.cc
+           dcmiod/libsrc/modenhequipment.cc
+           dcmiod/libsrc/modenhusimage.cc
+           dcmiod/libsrc/modenhusseries.cc
+           dcmiod/libsrc/modequipment.cc
+           dcmiod/libsrc/modfloatingpointimagepixel.cc
+           dcmiod/libsrc/modfor.cc
+           dcmiod/libsrc/modgeneralimage.cc
+           dcmiod/libsrc/modgeneralseries.cc
+           dcmiod/libsrc/modgeneralstudy.cc
+           dcmiod/libsrc/modhelp.cc
+           dcmiod/libsrc/modimagepixel.cc
+           dcmiod/libsrc/modimagepixelbase.cc
+           dcmiod/libsrc/modmultiframedimension.cc
+           dcmiod/libsrc/modmultiframefg.cc
+           dcmiod/libsrc/modpatient.cc
+           dcmiod/libsrc/modpatientstudy.cc
+           dcmiod/libsrc/modsegmentationseries.cc
+           dcmiod/libsrc/modsopcommon.cc
+           dcmiod/libsrc/modsynchronization.cc
+           dcmiod/libsrc/modusfor.cc
+           dcmiod/tests/timagepixel.cc
+           dcmseg/include/dcmtk/dcmseg/segdoc.h
+           dcmseg/libsrc/segdoc.cc
+           dcmseg/libsrc/segtypes.cc
+           dcmseg/tests/tconcat_binary.cc
+
+**** Changes from 2019.12.10 (onken)
+
+- New module dcmect for working with Enhanced CT:
+  Added new DCMTK module dcmect which facilitates creation, loading,
+  (partly) modification and storing Enhanced CT objects.
+  Also included is a general Concatenation API that allows to create and
+  re-assemble Concatenations from given DICOM datasets. The related
+  classes are called ConcatenationCreator and ConcatentionLoader and are
+  part of the dcmfg module. Right now, only uncompressed ("unencapsulated")
+  pixel data is supported.
+  The existing Segmentation API (dcmseg) as well as the new Enhanced CT API
+  (dcmect) both support writing and reading Concatenations via dedicated
+  methods.
+  Acknowledgement: Thanks to GE Aviation for sponsoring this feature.
+  Added:   configure
+           dcmect/CMakeLists.txt
+           dcmect/Makefile.in
+           dcmect/configure
+           dcmect/data/Makefile.in
+           dcmect/docs/Makefile.in
+           dcmect/docs/dcmect.dox
+           dcmect/etc/Makefile.in
+           dcmect/include/CMakeLists.txt
+           dcmect/include/Makefile.in
+           dcmect/include/dcmtk/dcmect/def.h
+           dcmect/include/dcmtk/dcmect/enhanced_ct.h
+           dcmect/include/dcmtk/dcmect/types.h
+           dcmect/libsrc/CMakeLists.txt
+           dcmect/libsrc/Makefile.dep
+           dcmect/libsrc/Makefile.in
+           dcmect/libsrc/enhanced_ct.cc
+           dcmect/libsrc/types.cc
+           dcmect/tests/CMakeLists.txt
+           dcmect/tests/Makefile.dep
+           dcmect/tests/Makefile.in
+           dcmect/tests/t_huge_concat.cc
+           dcmect/tests/t_roundtrip.cc
+           dcmect/tests/tests.cc
+           dcmfg/include/dcmtk/dcmfg/concatenationcreator.h
+           dcmfg/include/dcmtk/dcmfg/concatenationloader.h
+           dcmfg/include/dcmtk/dcmfg/fgctacquisitiondetails.h
+           dcmfg/include/dcmtk/dcmfg/fgctacquisitiontype.h
+           dcmfg/include/dcmtk/dcmfg/fgctadditionalxraysource.h
+           dcmfg/include/dcmtk/dcmfg/fgctexposure.h
+           dcmfg/include/dcmtk/dcmfg/fgctgeometry.h
+           dcmfg/include/dcmtk/dcmfg/fgctimageframetype.h
+           dcmfg/include/dcmtk/dcmfg/fgctposition.h
+           dcmfg/include/dcmtk/dcmfg/fgctreconstruction.h
+           dcmfg/include/dcmtk/dcmfg/fgcttabledynamics.h
+           dcmfg/include/dcmtk/dcmfg/fgctxraydetails.h
+           dcmfg/include/dcmtk/dcmfg/fgirradiationeventid.h
+           dcmfg/include/dcmtk/dcmfg/fgtemporalposition.h
+           dcmfg/libsrc/concatenationcreator.cc
+           dcmfg/libsrc/concatenationloader.cc
+           dcmfg/libsrc/fgctacquisitiondetails.cc
+           dcmfg/libsrc/fgctacquisitiontype.cc
+           dcmfg/libsrc/fgctadditionalxraysource.cc
+           dcmfg/libsrc/fgctexposure.cc
+           dcmfg/libsrc/fgctgeometry.cc
+           dcmfg/libsrc/fgctimageframetype.cc
+           dcmfg/libsrc/fgctposition.cc
+           dcmfg/libsrc/fgctreconstruction.cc
+           dcmfg/libsrc/fgcttabledynamics.cc
+           dcmfg/libsrc/fgctxraydetails.cc
+           dcmfg/libsrc/fgirradiationeventid.cc
+           dcmfg/libsrc/fgtemporalposition.cc
+           dcmfg/tests/t_concatenation_creator.cc
+           dcmfg/tests/t_concatenation_loader.cc
+           dcmfg/tests/t_ct_acquisition_details.cc
+           dcmfg/tests/t_ct_acquisition_type.cc
+           dcmfg/tests/t_ct_image_frame_type.cc
+           dcmfg/tests/t_ct_position.cc
+           dcmfg/tests/t_ct_table_dynamics.cc
+           dcmfg/tests/t_irradiation_event_identification.cc
+           dcmseg/tests/tconcat_binary.cc
+           dcmseg/tests/troundtrip.cc
+  Affects: CMakeLists.txt
+           Makefile
+           config/modules
+           config/tests/stack.cc
+           dcmdata/include/dcmtk/dcmdata/dcbytstr.h
+           dcmdata/include/dcmtk/dcmdata/dcerror.h
+           dcmdata/include/dcmtk/dcmdata/dcitem.h
+           dcmdata/include/dcmtk/dcmdata/dcvrds.h
+           dcmdata/libsrc/dcbytstr.cc
+           dcmdata/libsrc/dcitem.cc
+           dcmdata/libsrc/dcvrds.cc
+           dcmdata/tests/Makefile.dep
+           dcmdata/tests/tests.cc
+           dcmdata/tests/tvrds.cc
+           dcmfg/include/dcmtk/dcmfg/fg.h
+           dcmfg/include/dcmtk/dcmfg/fgbase.h
+           dcmfg/include/dcmtk/dcmfg/fgdefine.h
+           dcmfg/include/dcmtk/dcmfg/fgderimg.h
+           dcmfg/include/dcmtk/dcmfg/fgfact.h
+           dcmfg/include/dcmtk/dcmfg/fgfracon.h
+           dcmfg/include/dcmtk/dcmfg/fgframeanatomy.h
+           dcmfg/include/dcmtk/dcmfg/fgframevoilut.h
+           dcmfg/include/dcmtk/dcmfg/fgimagedatatype.h
+           dcmfg/include/dcmtk/dcmfg/fginterface.h
+           dcmfg/include/dcmtk/dcmfg/fgparametricmapframetype.h
+           dcmfg/include/dcmtk/dcmfg/fgpixeltransform.h
+           dcmfg/include/dcmtk/dcmfg/fgpixmsr.h
+           dcmfg/include/dcmtk/dcmfg/fgplanor.h
+           dcmfg/include/dcmtk/dcmfg/fgplanorvol.h
+           dcmfg/include/dcmtk/dcmfg/fgplanpo.h
+           dcmfg/include/dcmtk/dcmfg/fgplanposvol.h
+           dcmfg/include/dcmtk/dcmfg/fgrealworldvaluemapping.h
+           dcmfg/include/dcmtk/dcmfg/fgseg.h
+           dcmfg/include/dcmtk/dcmfg/fgtypes.h
+           dcmfg/include/dcmtk/dcmfg/fgusimagedescription.h
+           dcmfg/include/dcmtk/dcmfg/stack.h
+           dcmfg/include/dcmtk/dcmfg/stackinterface.h
+           dcmfg/libsrc/CMakeLists.txt
+           dcmfg/libsrc/Makefile.dep
+           dcmfg/libsrc/Makefile.in
+           dcmfg/libsrc/fg.cc
+           dcmfg/libsrc/fgbase.cc
+           dcmfg/libsrc/fgderimg.cc
+           dcmfg/libsrc/fgfact.cc
+           dcmfg/libsrc/fgfracon.cc
+           dcmfg/libsrc/fgframeanatomy.cc
+           dcmfg/libsrc/fgframevoilut.cc
+           dcmfg/libsrc/fgimagedatatype.cc
+           dcmfg/libsrc/fginterface.cc
+           dcmfg/libsrc/fgparametricmapframetype.cc
+           dcmfg/libsrc/fgpixeltransform.cc
+           dcmfg/libsrc/fgpixmsr.cc
+           dcmfg/libsrc/fgplanor.cc
+           dcmfg/libsrc/fgplanorvol.cc
+           dcmfg/libsrc/fgplanpo.cc
+           dcmfg/libsrc/fgplanposvol.cc
+           dcmfg/libsrc/fgrealworldvaluemapping.cc
+           dcmfg/libsrc/fgseg.cc
+           dcmfg/libsrc/fgtypes.cc
+           dcmfg/libsrc/fgusimagedescription.cc
+           dcmfg/libsrc/stack.cc
+           dcmfg/libsrc/stackinterface.cc
+           dcmfg/tests/CMakeLists.txt
+           dcmfg/tests/Makefile.dep
+           dcmfg/tests/Makefile.in
+           dcmfg/tests/t_deriv_image.cc
+           dcmfg/tests/t_frame_content.cc
+           dcmfg/tests/tests.cc
+           dcmiod/include/dcmtk/dcmiod/cielabutil.h
+           dcmiod/include/dcmtk/dcmiod/iodcommn.h
+           dcmiod/include/dcmtk/dcmiod/iodcontentitemmacro.h
+           dcmiod/include/dcmtk/dcmiod/ioddef.h
+           dcmiod/include/dcmtk/dcmiod/iodimage.h
+           dcmiod/include/dcmtk/dcmiod/iodmacro.h
+           dcmiod/include/dcmtk/dcmiod/iodreferences.h
+           dcmiod/include/dcmtk/dcmiod/iodrules.h
+           dcmiod/include/dcmtk/dcmiod/iodtypes.h
+           dcmiod/include/dcmtk/dcmiod/iodutil.h
+           dcmiod/include/dcmtk/dcmiod/modacquisitioncontext.h
+           dcmiod/include/dcmtk/dcmiod/modbase.h
+           dcmiod/include/dcmtk/dcmiod/modcommoninstanceref.h
+           dcmiod/include/dcmtk/dcmiod/modenhequipment.h
+           dcmiod/include/dcmtk/dcmiod/modenhusimage.h
+           dcmiod/include/dcmtk/dcmiod/modenhusseries.h
+           dcmiod/include/dcmtk/dcmiod/modequipment.h
+           dcmiod/include/dcmtk/dcmiod/modfloatingpointimagepixel.h
+           dcmiod/include/dcmtk/dcmiod/modfor.h
+           dcmiod/include/dcmtk/dcmiod/modgeneralimage.h
+           dcmiod/include/dcmtk/dcmiod/modgeneralseries.h
+           dcmiod/include/dcmtk/dcmiod/modgeneralstudy.h
+           dcmiod/include/dcmtk/dcmiod/modhelp.h
+           dcmiod/include/dcmtk/dcmiod/modimagepixel.h
+           dcmiod/include/dcmtk/dcmiod/modimagepixelbase.h
+           dcmiod/include/dcmtk/dcmiod/modimagepixelvariant.h
+           dcmiod/include/dcmtk/dcmiod/modmultiframedimension.h
+           dcmiod/include/dcmtk/dcmiod/modmultiframefg.h
+           dcmiod/include/dcmtk/dcmiod/modpatient.h
+           dcmiod/include/dcmtk/dcmiod/modpatientstudy.h
+           dcmiod/include/dcmtk/dcmiod/modsegmentationseries.h
+           dcmiod/include/dcmtk/dcmiod/modsopcommon.h
+           dcmiod/include/dcmtk/dcmiod/modsynchronisation.h
+           dcmiod/include/dcmtk/dcmiod/modusfor.h
+           dcmiod/libsrc/Makefile.dep
+           dcmiod/libsrc/cielabutil.cc
+           dcmiod/libsrc/iodcommn.cc
+           dcmiod/libsrc/iodcontentitemmacro.cc
+           dcmiod/libsrc/iodmacro.cc
+           dcmiod/libsrc/iodreferences.cc
+           dcmiod/libsrc/iodrules.cc
+           dcmiod/libsrc/iodtypes.cc
+           dcmiod/libsrc/iodutil.cc
+           dcmiod/libsrc/modacquisitioncontext.cc
+           dcmiod/libsrc/modbase.cc
+           dcmiod/libsrc/modcommoninstanceref.cc
+           dcmiod/libsrc/modenhequipment.cc
+           dcmiod/libsrc/modenhusimage.cc
+           dcmiod/libsrc/modenhusseries.cc
+           dcmiod/libsrc/modequipment.cc
+           dcmiod/libsrc/modfloatingpointimagepixel.cc
+           dcmiod/libsrc/modfor.cc
+           dcmiod/libsrc/modgeneralimage.cc
+           dcmiod/libsrc/modgeneralseries.cc
+           dcmiod/libsrc/modgeneralstudy.cc
+           dcmiod/libsrc/modhelp.cc
+           dcmiod/libsrc/modimagepixel.cc
+           dcmiod/libsrc/modimagepixelbase.cc
+           dcmiod/libsrc/modmultiframedimension.cc
+           dcmiod/libsrc/modmultiframefg.cc
+           dcmiod/libsrc/modpatient.cc
+           dcmiod/libsrc/modpatientstudy.cc
+           dcmiod/libsrc/modsegmentationseries.cc
+           dcmiod/libsrc/modsopcommon.cc
+           dcmiod/libsrc/modsynchronization.cc
+           dcmiod/libsrc/modusfor.cc
+           dcmiod/tests/Makefile.dep
+           dcmiod/tests/tcielabutil.cc
+           dcmiod/tests/timagepixel.cc
+           dcmpmap/libsrc/Makefile.dep
+           dcmpmap/libsrc/dpmparametricmapiod.cc
+           dcmseg/include/dcmtk/dcmseg/segdef.h
+           dcmseg/include/dcmtk/dcmseg/segdoc.h
+           dcmseg/include/dcmtk/dcmseg/segment.h
+           dcmseg/include/dcmtk/dcmseg/segtypes.h
+           dcmseg/include/dcmtk/dcmseg/segutils.h
+           dcmseg/libsrc/Makefile.dep
+           dcmseg/libsrc/segdoc.cc
+           dcmseg/libsrc/segment.cc
+           dcmseg/libsrc/segtypes.cc
+           dcmseg/libsrc/segutils.cc
+           dcmseg/tests/CMakeLists.txt
+           dcmseg/tests/Makefile.dep
+           dcmseg/tests/Makefile.in
+           dcmseg/tests/tests.cc
+           dcmseg/tests/tutils.cc
+           dcmtract/libsrc/Makefile.dep
+           doxygen/htmldocs.dox
+           ofstd/include/dcmtk/ofstd/ofmap.h
+           ofstd/tests/tmap.cc
+
+**** Changes from 2019.12.10 (schlamelcher)
+
+- Fixed various typos and whitespace errors:
+  Thanks to Peter Klotz <Peter.Klotz@ith-icoserve.com> for the suggested patch.
+  Affects: dcmdata/apps/mdfdsman.cc
+           dcmdata/data/SC.dump
+           dcmdata/data/VLP.dump
+           dcmdata/include/dcmtk/dcmdata/dcelem.h
+           dcmdata/libsrc/dcswap.cc
+           dcmimage/include/dcmtk/dcmimage/diqthash.h
+           dcmnet/include/dcmtk/dcmnet/diutil.h
+           dcmnet/include/dcmtk/dcmnet/scp.h
+           dcmnet/include/dcmtk/dcmnet/scu.h
+           dcmnet/libsrc/dimfind.cc
+           dcmnet/libsrc/dimget.cc
+           dcmpstat/apps/dcmprscu.cc
+           dcmpstat/apps/dcmpsrcv.cc
+           dcmqrdb/libsrc/dcmqrdbi.cc
+           dcmrt/include/dcmtk/dcmrt/drmdose.h
+           dcmsign/include/dcmtk/dcmsign/dcsignat.h
+           dcmwlm/libsrc/wldsfs.cc
+           docs/CHANGES.320
+           docs/CHANGES.342
+           docs/CHANGES.350
+           docs/CHANGES.352
+           docs/CHANGES.360
+           docs/CHANGES.362
+           docs/CHANGES.363
+           oflog/include/dcmtk/oflog/helpers/queue.h
+           oflog/libsrc/filter.cc
+           oflog/libsrc/timehelp.cc
+
+**** Changes from 2019.11.28 (riesmeier)
+
+- Do not install "dummy" CHANGES file:
+  Do not install the "dummy" CHANGES file from the main directory of the
+  source tree since it does not contain any useful information (after the
+  DCMTK has been installed).
+  Affects: CHANGES
+           CMakeLists.txt
+           Makefile
+           config/rootconf
+
+**** Changes from 2019.11.26 (riesmeier)
+
+- Added new option --limit-output to findscu:
+  Added new option to findscu and the underlying C++ classes that allows for
+  specifying the maximum number of responses written to file. Limiting the
+  number of responses written to file might be useful e.g. if the C-FIND-CANCEL
+  request does not prevent the SCP from sending further C-FIND-RSP messages.
+  Affects: dcmnet/apps/findscu.cc
+           dcmnet/docs/findscu.man
+           dcmnet/include/dcmtk/dcmnet/dfindscu.h
+           dcmnet/libsrc/dfindscu.cc
+
+**** Changes from 2019.11.20 (riesmeier)
+
+- Updated Context Group classes for DICOM 2019e:
+  Updated automatically generated Context Group classes for the 2019e edition
+  of the DICOM standard. All supported classes were updated, even though there
+  were not changes to all of them.
+  Affects: dcmsr/include/dcmtk/dcmsr/cmr/cid100.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid10013.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid10033.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid11.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid244.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid29.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4020.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4021.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4031.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid42.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid6147.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7021.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7181.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7445.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7452.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7453.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7464.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7469.h
+           dcmsr/libcmr/cid100.cc
+           dcmsr/libcmr/cid10013.cc
+           dcmsr/libcmr/cid10033.cc
+           dcmsr/libcmr/cid11.cc
+           dcmsr/libcmr/cid244.cc
+           dcmsr/libcmr/cid29.cc
+           dcmsr/libcmr/cid4020.cc
+           dcmsr/libcmr/cid4021.cc
+           dcmsr/libcmr/cid4031.cc
+           dcmsr/libcmr/cid42.cc
+           dcmsr/libcmr/cid6147.cc
+           dcmsr/libcmr/cid7021.cc
+           dcmsr/libcmr/cid7181.cc
+           dcmsr/libcmr/cid7445.cc
+           dcmsr/libcmr/cid7452.cc
+           dcmsr/libcmr/cid7453.cc
+           dcmsr/libcmr/cid7464.cc
+           dcmsr/libcmr/cid7469.cc
+
+- Updated code definitions for DICOM 2019e:
+  Updated automatically generated code definitions for coding scheme "DCM"
+  and "UMLS". For the coding scheme "NCIt", there were no changes.
+  Affects: dcmsr/include/dcmtk/dcmsr/codes/dcm.h
+           dcmsr/include/dcmtk/dcmsr/codes/ncit.h
+           dcmsr/include/dcmtk/dcmsr/codes/umls.h
+
+**** Changes from 2019.11.19 (riesmeier)
+
+- Updated data dictionary for DICOM 2019e:
+  Updated data dictionary for the latest edition of the DICOM standard.
+  Affects: dcmdata/data/dicom.dic
+           dcmdata/include/dcmtk/dcmdata/dcdeftag.h
+           dcmdata/libsrc/dcdictbi.cc
+
+**** Changes from 2019.11.19 (onken)
+
+- Clarified documentation for dcmodify:
+  Thanks to forum user "JustSomeGuy" for the report.
+  Affects: dcmdata/docs/dcmodify.man
+
+**** Changes from 2019.11.15 (riesmeier)
+
+- Implemented support for CP-1913 (FT):
+  Implemented support for CP-1913 "Coding Scheme Version requires Coding Scheme
+  Designator to be present", i.e. enhanced the checks in DSRCodedEntryValue.
+  Also added a new test case that explicitly checks for this combination.
+  Affects: dcmsr/libsrc/dsrcodvl.cc
+           dcmsr/tests/tsrcodvl.cc
+
+- Implemented support for CP-1893 (FT):
+  Implemented support for CP-1893 "Fix inconsistent Relationship Content
+  Constraints (SR IODs from Supplement 164)", i.e. removed Target Value Type
+  "TIME" from Relationship Content Constraints for Planned Imaging Agent
+  Administration SR IOD and Performed Imaging Agent Administration SR IOD.
+  Affects: dcmsr/libsrc/dsrpficc.cc
+           dcmsr/libsrc/dsrplicc.cc
+
+**** Changes from 2019.11.08 (riesmeier)
+
+- Fixed possible issue with getFullOverlayData():
+  Fixed issue with getFullOverlayData() that could cause a crash (segmentation
+  fault) when processing an overlay plane with an origin other than (0,0).
+  Note that the dcm2pnm/dcmj2pnm/dcml2pnm command line tool does not use this
+  method and is, therefore, not affected by this issue.
+  This closes DCMTK Bug #911.
+  Thanks to Bartosz Bialoskorski <bartoszbialoskorski@gmail.com> for the report
+  and the sample DICOM file.
+  Affects: dcmimgle/include/dcmtk/dcmimgle/diovpln.h
+           dcmimgle/libsrc/diovlay.cc
+           dcmimgle/libsrc/diovpln.cc
+
+**** Changes from 2019.10.31 (riesmeier)
+
+- Updated Context Group classes for DICOM 2019d:
+  Updated automatically generated Context Group classes for the 2019d edition
+  of the DICOM standard. All supported classes were updated, even though there
+  were not changes to all of them.
+  Affects: dcmsr/include/dcmtk/dcmsr/cmr/cid100.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid10013.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid10033.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid11.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid244.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid29.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4020.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4021.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid4031.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid42.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid6147.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7021.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7181.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7445.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7452.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7453.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7464.h
+           dcmsr/include/dcmtk/dcmsr/cmr/cid7469.h
+           dcmsr/libcmr/cid100.cc
+           dcmsr/libcmr/cid10013.cc
+           dcmsr/libcmr/cid10033.cc
+           dcmsr/libcmr/cid11.cc
+           dcmsr/libcmr/cid244.cc
+           dcmsr/libcmr/cid29.cc
+           dcmsr/libcmr/cid4020.cc
+           dcmsr/libcmr/cid4021.cc
+           dcmsr/libcmr/cid4031.cc
+           dcmsr/libcmr/cid42.cc
+           dcmsr/libcmr/cid6147.cc
+           dcmsr/libcmr/cid7021.cc
+           dcmsr/libcmr/cid7181.cc
+           dcmsr/libcmr/cid7445.cc
+           dcmsr/libcmr/cid7452.cc
+           dcmsr/libcmr/cid7453.cc
+           dcmsr/libcmr/cid7464.cc
+           dcmsr/libcmr/cid7469.cc
+
+- Updated code definitions for DICOM 2019d:
+  Updated automatically generated code definitions for coding scheme "DCM"
+  and "NCIt". For the coding scheme "UMLS", there were no changes.
+  Affects: dcmsr/include/dcmtk/dcmsr/codes/dcm.h
+           dcmsr/include/dcmtk/dcmsr/codes/ncit.h
+
+- Updated data dictionary for DICOM 2019d:
+  Updated data dictionary for the latest edition of the DICOM standard.
+  Affects: dcmdata/data/dicom.dic
+           dcmdata/include/dcmtk/dcmdata/dcdeftag.h
+           dcmdata/libsrc/dcdictbi.cc
+           dcmrt/libsrc/drtrbs4.cc
+           dcmrt/libsrc/drtrbs8.cc
+
+**** Changes from 2019.10.29 (riesmeier)
+
+- Enhanced performance of getting a sequence item:
+  Significantly enhanced performance of getting an item from the end of a
+  DcmSequenceOfItems or DcmPixelSequence instance. These enhancements are
+  based on an improved version of the DcmList::seek_to() method.
+  Affects: dcmdata/libsrc/dclist.cc
+           dcmdata/tests/tsequen.cc
+
+- Enhanced performance of inserting sequence items:
+  Significantly enhanced the performance of inserting items at the end of a
+  DcmSequenceOfItems or DcmPixelSequence instance. These enhancements are
+  based on a smarter use of the underlying DcmList class.
+  Adding 99,999 items to a pixel sequence now only takes a fraction of a
+  second compared to a very large number of seconds (as it was before).
+  Also clarified that the item-related helper methods in the DcmItem class,
+  such as findAndGetSequenceItem(), cannot be used with an instance of the
+  DcmPixelItem class (since this class is not derived from DcmItem).
+  Added:   dcmdata/tests/tsequen.cc
+  Affects: dcmdata/include/dcmtk/dcmdata/dcitem.h
+           dcmdata/libsrc/dcitem.cc
+           dcmdata/libsrc/dcpixseq.cc
+           dcmdata/libsrc/dcsequen.cc
+           dcmdata/tests/CMakeLists.txt
+           dcmdata/tests/Makefile.in
+           dcmdata/tests/tests.cc
+
+- Fixed typos and other minor issues.
+  Affects: INSTALL
+           ofstd/libsrc/ofstring.cc
+
+**** Changes from 2019.10.29 (schlamelcher)
+
+- Updated version information for 3.6.5+ development:
+  Updated version information marking the start of DCMTK development post minor
+  release 3.6.5.
+  Moved official ANNOUNCE file of the DCMTK release 3.6.5 to the "docs"
+  subfolder and replaced the main ANNOUNCE file with a "dummy".
+  Added:   docs/ANNOUNCE.365
+  Affects: ANNOUNCE
+           CMake/dcmtkPrepare.cmake
+           VERSION
+           config/configure
+           config/configure.in
index d39904b24b679b2b207cb9af4c68a7ed83be9498..41c349a05b8a2b95c4ef4871d9d6fb3283fdddfd 100644 (file)
@@ -31,6 +31,7 @@ man:
            manpages.cfg > manpages.tmp
        $(DOXYGEN) manpages.tmp
        rm -f manpages/man1/*.man.1
+       rm -f manpages/man1/_*_.1
        ./patchman.sh
 
 text:
index b4ecff75c6550410c7f00bdd246031ea73d4aa4e..427e3ac3c31ee4596944e541f6b213a6b87835b3 100644 (file)
@@ -10,6 +10,7 @@ DCMTK contains the following sub-packages, each in its own sub-directory:
 
 \li \ref mod_config
 \li \ref mod_dcmdata
+\li \ref mod_dcmect
 \li \ref mod_dcmfg
 \li \ref mod_dcmimage
 \li \ref mod_dcmimgle
index 757eb2750248d370c94397849b0f30d0e6c26f2f..92985e99d861ffa4d7db7d5e3bfdbccde92a4a57 100644 (file)
@@ -1,4 +1,4 @@
-.TH "cda2dcm" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "cda2dcm" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 cda2dcm \- Encapsulate CDA file into DICOM file format
@@ -169,6 +169,31 @@ data set trailing padding (not with --write-dataset):
          and items on multiple of i bytes
 .fi
 .PP
+.SH "NOTES"
+.PP
+.SS "Attribute Sources"
+The application may be fed with some additional input for filling mandatory (and optional) attributes in the new DICOM file like patient, study and series information:
+.PP
+.PD 0
+.IP "\(bu" 2
+The \fI--key\fP option can be used to add further attributes to the DICOM output file\&.
+.PP
+.PD 0
+.IP "\(bu" 2
+It is also possible to specify sequences, items and nested attributes using the \fI--key\fP option\&. In these cases, a special 'path' notation has to be used\&. Details on this path notation can be found in the documentation of \fBdcmodify\fP\&.
+.PP
+.PD 0
+.IP "\(bu" 2
+The \fI--key\fP option can be present more than once\&.
+.PP
+.PD 0
+.IP "\(bu" 2
+The value part (after the '=') may be absent causing the attribute to be set with zero length\&.
+.PP
+.PD 0
+.IP "\(bu" 2
+Please be advised that the \fI--key\fP option is applied at the very end, just before saving the DICOM file, so there is no value checking whatsoever\&.
+.PP
 .SH "LOGGING"
 .PP
 The level of logging output of the various command line tools and underlying libraries can be specified by the user\&. By default, only errors and warnings are written to the standard error stream\&. Using option \fI--verbose\fP also informational messages like processing details are reported\&. Option \fI--debug\fP can be used to get more details on the internal activity, e\&.g\&. for debugging purposes\&. Other logging levels can be selected using option \fI--log-level\fP\&. In \fI--quiet\fP mode only fatal errors are reported\&. In such very severe error events, the application will usually terminate\&. For more details on the different logging levels, see documentation of module 'oflog'\&.
@@ -213,4 +238,4 @@ The \fBcda2dcm\fP utility will attempt to load DICOM data dictionaries specified
 The default behavior should be preferred and the \fIDCMDICTPATH\fP environment variable only used when alternative data dictionaries are required\&. The \fIDCMDICTPATH\fP environment variable has the same format as the Unix shell \fIPATH\fP variable in that a colon (':') separates entries\&. On Windows systems, a semicolon (';') is used as a separator\&. The data dictionary code will attempt to load each file specified in the \fIDCMDICTPATH\fP environment variable\&. It is an error if no data dictionary can be loaded\&.
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 2018 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 2018-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index 36599b10c8583e4f3de79eb5f1467217ae58effe..e59f3447edbc29ec922276fbe212f89612f61070 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcm2json" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcm2json" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcm2json \- Convert DICOM file and data set to JSON
@@ -14,7 +14,7 @@ dcm2json [options] dcmfile-in [jsonfile-out]
 .PP
 The \fBdcm2json\fP utility converts the contents of a DICOM file (file format or raw data set) to JSON (JavaScript Object Notation)\&. The output refers to the 'DICOM JSON Model', which is found in DICOM Part 18 Section F\&.
 .PP
-If \fBdcm2json\fP reads a raw data set (DICOM data without a file format meta-header) it will attempt to guess the transfer syntax by examining the first few bytes of the file\&. It is not always possible to correctly guess the transfer syntax and it is better to convert a data set to a file format whenever possible (using the \fBdcmconv\fP utility)\&. It is also possible to use the \fI-f\fP and \fI-t[ieb]\fP options to force \fBdcm2json\fP to read a data set with a particular transfer syntax\&.
+If \fBdcm2json\fP reads a raw data set (DICOM data without a file format meta-header), it will attempt to guess the transfer syntax by examining the first few bytes of the file\&. It is not always possible to correctly guess the transfer syntax and it is better to convert a data set to a file format whenever possible (using the \fBdcmconv\fP utility)\&. It is also possible to use the \fI-f\fP and \fI-t[ieb]\fP options to force \fBdcm2json\fP to read a data set with a particular transfer syntax\&.
 .SH "PARAMETERS"
 .PP
 .PP
@@ -29,30 +29,30 @@ jsonfile-out  JSON output filename (default: stdout)
 .SS "general options"
 .PP
 .nf
-  -h    --help
-          print this help text and exit
+  -h   --help
+         print this help text and exit
 
-        --version
-          print version information and exit
+       --version
+         print version information and exit
 
-        --arguments
-          print expanded command line arguments
+       --arguments
+         print expanded command line arguments
 
-  -q    --quiet
-          quiet mode, print no warnings and errors
+  -q   --quiet
+         quiet mode, print no warnings and errors
 
-  -v    --verbose
-          verbose mode, print processing details
+  -v   --verbose
+         verbose mode, print processing details
 
-  -d    --debug
-          debug mode, print debug information
+  -d   --debug
+         debug mode, print debug information
 
-  -ll   --log-level  [l]evel: string constant
-          (fatal, error, warn, info, debug, trace)
-          use level l for the logger
+  -ll  --log-level  [l]evel: string constant
+         (fatal, error, warn, info, debug, trace)
+         use level l for the logger
 
-  -lc   --log-config  [f]ilename: string
-          use config file f for the logger
+  -lc  --log-config  [f]ilename: string
+         use config file f for the logger
 .fi
 .PP
 .SS "input options"
@@ -60,31 +60,42 @@ jsonfile-out  JSON output filename (default: stdout)
 .nf
 input file format:
 
-  +f    --read-file
-          read file format or data set (default)
+  +f   --read-file
+         read file format or data set (default)
 
-  +fo   --read-file-only
-          read file format only
+  +fo  --read-file-only
+         read file format only
 
-  -f    --read-dataset
-          read data set without file meta information
+  -f   --read-dataset
+         read data set without file meta information
 
 input transfer syntax:
 
-  -t=   --read-xfer-auto
-          use TS recognition (default)
+  -t=  --read-xfer-auto
+         use TS recognition (default)
 
-  -td   --read-xfer-detect
-          ignore TS specified in the file meta header
+  -td  --read-xfer-detect
+         ignore TS specified in the file meta header
 
-  -te   --read-xfer-little
-          read with explicit VR little endian TS
+  -te  --read-xfer-little
+         read with explicit VR little endian TS
 
-  -tb   --read-xfer-big
-          read with explicit VR big endian TS
+  -tb  --read-xfer-big
+         read with explicit VR big endian TS
 
-  -ti   --read-xfer-implicit
-          read with implicit VR little endian TS
+  -ti  --read-xfer-implicit
+         read with implicit VR little endian TS
+.fi
+.PP
+.SS "processing options"
+.PP
+.nf
+encoding of infinity and not-a-number:
+  -es  --encode-strict
+         report error for 'inf' and 'nan' (default)
+
+  -ee  --encode-extended
+         permit 'inf' and 'nan' in JSON numbers
 .fi
 .PP
 .SS "output options"
@@ -92,18 +103,18 @@ input transfer syntax:
 .nf
 output format:
 
-  +fc   --formatted-code
-          enable whitespace formatting (default)
+  +fc  --formatted-code
+         enable whitespace formatting (default)
 
-          # prints additional spaces and newlines for increased
-          # readability
+         # prints additional spaces and newlines for increased
+         # readability
 
-  -fc   --compact-code
-          print only required characters
+  -fc  --compact-code
+         print only required characters
 
-  +m    --write-meta
-          write data set with meta information
-          (warning: not conforming to the DICOM standard)
+  +m   --write-meta
+         write data set with meta information
+         (warning: not conforming to the DICOM standard)
 .fi
 .PP
 .SH "JSON Format"
@@ -268,11 +279,11 @@ The basic structure of the JSON output created from a DICOM file looks like the
 .fi
 .PP
 .SS "Bulk Data"
-Binary data, i\&.e\&. DICOM element values with Value Representations (VR) of OB or OW, as well as OD, OF and UN values are by default not written to the JSON output because of their size\&. Instead, for each element, a new Universally Unique Identifier (UUID) is being generated and written as an value of a BulkDataURI JSON element\&. So far, there is no possibility to write an additional file to hold the binary data for each of the binary data chunks\&.
+Binary data, i\&.e\&. DICOM element values with Value Representations (VR) of OB or OW, as well as OD, OF, OL, OV and UN values are always written as 'InlineBinary' (base64 encoding) to the JSON output\&. A future version of this tool might optionally use a 'BulkDataURI' instead, i\&.e\&. the WADO-RS URL of a bulk data item that contains the element value\&. This would be particularly useful for large amounts of data, such as pixel data\&.
 .SH "NOTES"
 .PP
 .SS "Character Encoding"
-\fBdcm2json\fP always tries to output in UTF-8 encoding\&. If this is not possible, e\&.g\&. because there is no support for character set conversion, ASCII is used instead (which is a subset of UTF-8)\&.
+As required by the DICOM JSON encoding, \fBdcm2json\fP always creates output in Unicode UTF-8 encoding and converts DICOM datasets accordingly\&. If this is not possible, for example because DCMTK has been compiled without either iconv or ICU library, an error is returned\&.
 .SH "LOGGING"
 .PP
 The level of logging output of the various command line tools and underlying libraries can be specified by the user\&. By default, only errors and warnings are written to the standard error stream\&. Using option \fI--verbose\fP also informational messages like processing details are reported\&. Option \fI--debug\fP can be used to get more details on the internal activity, e\&.g\&. for debugging purposes\&. Other logging levels can be selected using option \fI--log-level\fP\&. In \fI--quiet\fP mode only fatal errors are reported\&. In such very severe error events, the application will usually terminate\&. For more details on the different logging levels, see documentation of module 'oflog'\&.
@@ -285,6 +296,36 @@ All command line tools use the following notation for parameters: square bracket
 Command line options are distinguished from parameters by a leading '+' or '-' sign, respectively\&. Usually, order and position of command line options are arbitrary (i\&.e\&. they can appear anywhere)\&. However, if options are mutually exclusive the rightmost appearance is used\&. This behavior conforms to the standard evaluation rules of common Unix shells\&.
 .PP
 In addition, one or more command files can be specified using an '@' sign as a prefix to the filename (e\&.g\&. \fI@command\&.txt\fP)\&. Such a command argument is replaced by the content of the corresponding text file (multiple whitespaces are treated as a single separator unless they appear between two quotation marks) prior to any further evaluation\&. Please note that a command file cannot contain another command file\&. This simple but effective approach allows one to summarize common combinations of options/parameters and avoids longish and confusing command lines (an example is provided in file \fI<datadir>/dumppat\&.txt\fP)\&.
+.SH "EXIT CODES"
+.PP
+The \fBdcm2json\fP utility uses the following exit codes when terminating\&. This enables the user to check for the reason why the application terminated\&.
+.SS "general"
+.PP
+.nf
+EXITCODE_NO_ERROR                         0
+EXITCODE_COMMANDLINE_SYNTAX_ERROR         1
+.fi
+.PP
+.SS "input file errors"
+.PP
+.nf
+EXITCODE_CANNOT_READ_INPUT_FILE          20
+EXITCODE_NO_INPUT_FILES                  21
+.fi
+.PP
+.SS "output file errors"
+.PP
+.nf
+EXITCODE_CANNOT_WRITE_OUTPUT_FILE        40
+.fi
+.PP
+.SS "processing errors"
+.PP
+.nf
+EXITCODE_CANNOT_CONVERT_TO_UNICODE       80
+EXITCODE_CANNOT_WRITE_VALID_JSON         81
+.fi
+.PP
 .SH "ENVIRONMENT"
 .PP
 The \fBdcm2json\fP utility will attempt to load DICOM data dictionaries specified in the \fIDCMDICTPATH\fP environment variable\&. By default, i\&.e\&. if the \fIDCMDICTPATH\fP environment variable is not set, the file \fI<datadir>/dicom\&.dic\fP will be loaded unless the dictionary is built into the application (default for Windows)\&.
@@ -292,4 +333,4 @@ The \fBdcm2json\fP utility will attempt to load DICOM data dictionaries specifie
 The default behavior should be preferred and the \fIDCMDICTPATH\fP environment variable only used when alternative data dictionaries are required\&. The \fIDCMDICTPATH\fP environment variable has the same format as the Unix shell \fIPATH\fP variable in that a colon (':') separates entries\&. On Windows systems, a semicolon (';') is used as a separator\&. The data dictionary code will attempt to load each file specified in the \fIDCMDICTPATH\fP environment variable\&. It is an error if no data dictionary can be loaded\&.
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 2016-2017 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 2016-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index 91e2a6690c6067f9d52eb16dad34423e8f5a2add..567d785059434163f8a9ef69b546383f81c9ba9d 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcm2pdf" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcm2pdf" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcm2pdf \- Extract PDF file from DICOM encapsulated PDF
index d739b52be00de7987e0bdd2b7a9193023a50b8ad..6da251720ee6141f87d949f3dfe37a1bf0ac139f 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcm2pnm" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcm2pnm" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcm2pnm \- Convert DICOM images to PGM/PPM, PNG, TIFF or BMP
@@ -124,7 +124,7 @@ flipping:
 scaling:
 
   +a    --recognize-aspect
-          recognize pixel aspect ratio (default)
+          recognize pixel aspect ratio when scaling (default)
 
   -a    --ignore-aspect
           ignore pixel aspect ratio when scaling
@@ -325,7 +325,7 @@ PNG format:
 other transformations:
 
   +G    --grayscale
-          convert to grayscale if necessary
+          convert color image to grayscale (monochrome)
 
   +P    --change-polarity
           change polarity (invert pixel output)
@@ -452,4 +452,4 @@ The default behavior should be preferred and the \fIDCMDICTPATH\fP environment v
 \fBdcmj2pnm\fP(1), \fBimg2dcm\fP(1)
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 1998-2014 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 1998-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index 72f1554cf48a77b8bc2a0ae8de38988b8d0042d1..a47019298b057af8c2ef7784053625a8f6733286 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcm2xml" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcm2xml" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcm2xml \- Convert DICOM file and data set to XML
@@ -204,7 +204,7 @@ The basic structure of the DCMTK-specific XML output created from a DICOM file l
       <item card="3">
         <element tag="0028,3002" vr="xs" vm="3" len="6"
                  name="LUTDescriptor">
-          256\\0\\8
+          256\0\8
         </element>
         ...
       </item>
@@ -230,11 +230,11 @@ Multiple values (i\&.e\&. where the DICOM value multiplicity is greater than 1)
 .PP
 The description of the Native DICOM Model format can be found in the DICOM standard, part 19 ('Application Hosting')\&.
 .SS "Bulk Data"
-Binary data, i\&.e\&. DICOM element values with Value Representations (VR) of OB or OW, as well as OD, OF, OV and UN values are by default not written to the XML output because of their size\&. Instead, for each element, a new Universally Unique Identifier (UUID) is being generated and written as an attribute of a <BulkData> XML element\&. So far, there is no possibility to write an additional file to hold the binary data for each of the binary data chunks\&. This is not required by the standard, however, it might be useful for implementing an Application Hosting interface; thus this feature may be available in future versions of \fBdcm2xml\fP\&.
+Binary data, i\&.e\&. DICOM element values with Value Representations (VR) of OB or OW, as well as OD, OF, OL, OV and UN values are by default not written to the XML output because of their size\&. Instead, for each element, a new Universally Unique Identifier (UUID) is being generated and written as an attribute of a <BulkData> XML element\&. So far, there is no possibility to write an additional file to hold the binary data for each of the binary data chunks\&. This is not required by the standard, however, it might be useful for implementing an Application Hosting interface; thus this feature may be available in future versions of \fBdcm2xml\fP\&.
 .PP
-In addition, Supplement 163 (Store Over the Web by Representational State Transfer Services) introduces a new <InlineBinary> XML element that allows for encoding binary data as Base64\&. Currently, the command line option \fI--encode-base64\fP enables this encoding for the following VRs: OB, OD, OF, OV, OW and UN\&.
+In addition, Supplement 163 (Store Over the Web by Representational State Transfer Services) introduces a new <InlineBinary> XML element that allows for encoding binary data as Base64\&. Currently, the command line option \fI--encode-base64\fP enables this encoding for the following VRs: OB, OD, OF, OL, OV, OW and UN\&.
 .SS "Known Issues"
-In addition to what is written in the above section on 'Bulk Data', there are further known issues with the current implementation of the Native DICOM Model format\&. For example, large element values with a VR other than OB, OD, OF, OV, OW or UN are currently never written as bulk data, although it might be useful, e\&.g\&. for very long text elements (especially UT) or very long numeric fields (of various VRs)\&.
+In addition to what is written in the above section on 'Bulk Data', there are further known issues with the current implementation of the Native DICOM Model format\&. For example, large element values with a VR other than OB, OD, OF, OL, OV, OW or UN are currently never written as bulk data, although it might be useful, e\&.g\&. for very long text elements (especially UT) or very long numeric fields (of various VRs)\&.
 .SH "NOTES"
 .PP
 .SS "Character Encoding"
@@ -286,4 +286,4 @@ The default behavior should be preferred and the \fIDCMDICTPATH\fP environment v
 \fBxml2dcm\fP(1), \fBdcmconv\fP(1)
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 2002-2019 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 2002-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index 67cdca114769943ee2e0de1aaaa5ec4513414f39..8b2295453dca987a243fabfa71c86392d23d92e1 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmcjpeg" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmcjpeg" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmcjpeg \- Encode DICOM file to JPEG transfer syntax
index f8ac8bc41e74e28678027ecefd6c91ba20dd0981..686582d6b9b7a9c499f5f54b43b7afa464471d2d 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmcjpls" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmcjpls" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmcjpls \- Encode DICOM file to JPEG-LS transfer syntax
@@ -160,13 +160,6 @@ JPEG-LS interleave:
   # In sample-interleave mode each pixel's components are encoded before
   # the next pixel is encoded.
 
-  +in  --interleave-none
-         force uninterleaved JPEG-LS images
-
-  # This flag forces uninterleaved mode for the resulting image.
-  # In this mode, each of the image's components are completely encoded
-  # before the next component is handled.
-
   +iv  --interleave-default
          use the fastest possible interleave mode
 
@@ -345,4 +338,4 @@ The default behavior should be preferred and the \fIDCMDICTPATH\fP environment v
 \fBdcmdjpls\fP(1)
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 2009-2019 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 2009-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index cc6d6033decde7a63a649edc96cdac974c038f70..bad701c76efbe2bc7081b55de7091d7d62ec5ac4 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmconv" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmconv" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmconv \- Convert DICOM file encoding
@@ -243,11 +243,11 @@ other processing options:
 .nf
 output file format:
 
-  +F   --write-file
-         write file format (default)
-
   +Fm  --write-new-meta-info
-         write file format with new meta information
+         write file format with new meta information (default)
+
+  +F   --write-file
+         write file format
 
   -F   --write-dataset
          write data set without file meta information
@@ -347,4 +347,4 @@ The default behavior should be preferred and the \fIDCMDICTPATH\fP environment v
 \fBdcmdump\fP(1)
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 1994-2017 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 1994-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index d02e8c1c18b79cd4465b7ee2d3f5117caf98758f..ded40cfadb3b97faf51fcd7c3b4f8cd0eec5bd3d 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmcrle" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmcrle" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmcrle \- Encode DICOM file to RLE transfer syntax
index 7a2e7395959e33007c99daf841b35a1d49e1b243..238485a1c42f508bfae085c327d38cc2c12eb8b9 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmdjpeg" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmdjpeg" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmdjpeg \- Decode JPEG-compressed DICOM file
index 1ce5cc83c3ae09aa9daf57e5704c609581cb45a4..d2a75b3b6ccc857eecf199414b6d16c88947c5de 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmdjpls" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmdjpls" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmdjpls \- Decode JPEG-LS compressed DICOM file
index 4e016c4be0639b0afbdf3a7e43034af008958496..8c7fe207fa8a79de7fecadbb2c8e9182a5eaa420 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmdrle" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmdrle" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmdrle \- Decode RLE-compressed DICOM file
index 6c2fd3a0c2a7c488f79bf9fdb846c0a728fb4420..37d6dd4fb004cbbb3f0b67a7acd7e569fcf8e540 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmdspfn" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmdspfn" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmdspfn \- Export standard display curves to a text file
index 0071f849be0009356fcf969f859695d971625d2a..fd00a35e83e9de5b4e139a87bcc66a28ee182a5f 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmdump" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmdump" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmdump \- Dump DICOM file and data set
index 321640455bf4eea03ddfc0b60a2bd1602f6607d0..8c35a96bba1a14d875fcc16a15be15826bab03c5 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmftest" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmftest" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmftest \- Test if file uses DICOM part 10 format
index 51031df5e858ace16b84564266e3a3bce1edb44c..884079b74dc5788240b83c16d15e49187f07ce8f 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmgpdir" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmgpdir" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmgpdir \- Create a general purpose DICOMDIR
index 25f668bf38566c91a70d322268d421420db416b0..9426d936e8c5803981c778602eac946c6f7b4258 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmicmp" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmicmp" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmicmp \- Compare DICOM images and compute difference metrics
index 942ee2ac06d4a3215ccbc98ef788a668fca96862..217851030800a91d135326ca517eb4e3fac99e26 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmj2pnm" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmj2pnm" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmj2pnm \- Convert DICOM images to PGM/PPM, PNG, TIFF, JPEG or BMP
@@ -124,7 +124,7 @@ flipping:
 scaling:
 
   +a    --recognize-aspect
-          recognize pixel aspect ratio (default)
+          recognize pixel aspect ratio when scaling (default)
 
   -a    --ignore-aspect
           ignore pixel aspect ratio when scaling
@@ -394,7 +394,7 @@ JPEG format:
 other transformations:
 
   +G    --grayscale
-          convert to grayscale if necessary
+          convert color image to grayscale (monochrome)
 
   +P    --change-polarity
           change polarity (invert pixel output)
@@ -530,4 +530,4 @@ The default behavior should be preferred and the \fIDCMDICTPATH\fP environment v
 \fBdcm2pnm\fP(1), \fBimg2dcm\fP(1)
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 2001-2018 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 2001-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index 4805c7858e52bd546e21fe8f26fa3cc02a2cc174..6b30e479f65e59d72fd379af96f1bfb6714e2969 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcml2pnm" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcml2pnm" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcml2pnm \- Convert DICOM images to PGM/PPM, PNG, TIFF or BMP
@@ -124,7 +124,7 @@ flipping:
 scaling:
 
   +a    --recognize-aspect
-          recognize pixel aspect ratio (default)
+          recognize pixel aspect ratio when scaling (default)
 
   -a    --ignore-aspect
           ignore pixel aspect ratio when scaling
@@ -325,7 +325,7 @@ PNG format:
 other transformations:
 
   +G    --grayscale
-          convert to grayscale if necessary
+          convert color image to grayscale (monochrome)
 
   +P    --change-polarity
           change polarity (invert pixel output)
@@ -454,4 +454,4 @@ The default behavior should be preferred and the \fIDCMDICTPATH\fP environment v
 \fBdcm2pnm\fP(1), \fBimg2dcm\fP(1)
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 2001-2014 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 2001-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index a66766a7f575c605c9767efedbfaa6ebfa5f5cf8..7c840a1c7ceeaca958b2098c65bf6b11cc5f25b1 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmmkcrv" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmmkcrv" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmmkcrv \- Add 2D curve data to image
index cc7c784a48d2cc61ede65f249ee522ebff610da2..982ef18be49ef35315d6c450e05c2a2ecb584c27 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmmkdir" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmmkdir" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmmkdir \- Create a DICOMDIR file
index 8870b8c791ca869500157697422df18a81c6c22b..64a0627038fea5013231ba5e317773bf90d6104f 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmmklut" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmmklut" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmmklut \- Create DICOM look-up tables
index a87f9b0e4382933356b868d0f66a0f910c55ca6d..164f6394f2bc9592c2fb6f1459443b225936e7ca 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmodify" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmodify" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmodify \- Modify DICOM files
@@ -30,6 +30,8 @@ where 'sequence' is a sequence tag like (0008,1111) or a dictionary name for a t
 .PP
 When inserting tag paths consisting of multiple nodes (i\&.e\&. not a single element) using the \fI-i\fP option, any missing path elements (items, sequences, leaf elements) are inserted automatically when missing\&. That does not work for item wildcards: When no single item exists in the surrounding sequence \fBdcmodify\fP of course can't decide, how many items should be generated\&. However, if specifying an item number like '5', all 6 items (counted from zero) can be (and are) automatically generated in insert mode\&. If already 2 items would exist, the rest (4) would be inserted\&.
 .PP
+\fBdcmodify\fP does not work on directories, i\&.e\&. the parameter \fIdcmfile-in\fP\&.\&.\&. must not include directory names\&.
+.PP
 Please note that there are some issues concerning the modification of private tags (see PRIVATE TAGS section) and for changing UIDs (CHANGING UIDs section)\&.
 .SH "PARAMETERS"
 .PP
@@ -292,6 +294,8 @@ For the deletion of private non-reservation tags there are no special issues\&.
 If you generate new UID's with \fI-gst\fP, \fI-gse\fP or \fI-gin\fP, this will only affect the UID you chose to generate\&. So if you use \fI-gst\fP to generate a new 'Study Instance UID', then 'Series Instance UID' and 'SOP Instance UID' will not be affected! This gives you the possibility to generate each value separately\&. Normally, you would also modify the 'underlying' UIDs\&. As a disadvantage of this flexibility, the user has to assure, that when creating 'new' DICOM files with new UIDs with \fBdcmodify\fP, other UIDs have to be updated by the user as necessary\&.
 .PP
 When choosing the \fI-gin\fP option, the related metaheader tag ('Media Storage SOP Instance UID') is updated automatically\&. This behavior cannot be disabled\&.
+.PP
+When working on multiple input files, \fBdcmodify\fP processes each file in isolated fashion, i\&.e\&. it will generate UIDs for each single file\&. For example, when using the \fI-gst\fP option, \fBdcmodify\fP will insert a different Study Instance UID into each file instead of generating a single one and writing it to each file that is being processed\&.
 .SH "CREATING NEW FILES"
 .PP
 Option \fI--create-file\fP lets \fBdcmodify\fP create a file if it does not already exist on disk\&. This can be used in order to create files from scratch by performing consecutive insertions with options like \fI--insert\fP\&. This might especially become handy when creating query files for tools like \fBfindscu\fP or \fBmovescu\fP\&. In case no specific output transfer syntax is defined, \fBdcmodify\fP chooses Little Endian Explicit Uncompressed for output\&. Files that are newly created are always written as DICOM file format, i\&.e\&. option \fI--write-dataset\fP is not permitted together with \fI--create\fP\&. This way, at least the metaheader is written and no file with zero byte length is created in a case where no insertions are performed in the \fBdcmodify\fP call\&.
index 3b16c7bd43f513f7901d271ce5d96fe6b82b9b20..15673c80fa00bb4edca13a7b1a0068d0b00ae311 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmp2pgm" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmp2pgm" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmp2pgm \- Read DICOM image and presentation state and render bitmap
index 3d94739fab087141090f241fe2b7fef1d8d3cfe0..2bb8be7ba0ddefa7e78ec5461d15799d86176f37 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmprscp" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmprscp" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmprscp \- DICOM basic grayscale print management SCP
index 3fa9110486172abc79cd30d9cdc05a42cce99fca..a1394c1028dc1996c04e7e42ca01bb90ca800fce 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmprscu" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmprscu" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmprscu \- Print spooler for presentation state viewer
index 61d4ec77e5e82cc4324e19f698d4c93b720f2a01..50fe37c2e8c76e86d4680d74be0f0d4cc087ba5a 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmpschk" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmpschk" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmpschk \- Checking tool for presentation states
index e5742b745f1f13e894abc6147a4b2904b9465911..ee7b233fb42cc33f07d9da46aa1ef884338be9e2 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmpsmk" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmpsmk" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmpsmk \- Create DICOM grayscale softcopy presentation state
index 187cfb09bee7c84c70ce999d9cd80f3704fda5d4..7e4f05ff84ff75ce2653ad9c0265eab885b9cda2 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmpsprt" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmpsprt" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmpsprt \- Read DICOM images and presentation states and render print job
index f0f46548af5c1e10af176ce1f337eca1f65a3eee..13941623aa39062a88cf67597728f0009a5da29d 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmpsrcv" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmpsrcv" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmpsrcv \- Network receive for presentation state viewer
index 5a1402402120407626dc61e41b841546a9d6558f..ee067c0f986af7f61c473c97c55f02a2b3cd589e 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmpssnd" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmpssnd" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmpssnd \- Network send for presentation state viewer
index 5fb96897733566d2c3b478676b60e5f173812b01..b6112c5c6280a97c39c2f22800a7cb37599f1b93 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmqridx" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmqridx" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmqridx \- Register a DICOM image file in an image database index file
index ef668f0ba7c1e7acfd48a31a9debf2b56a16c7bd..47f9ba712a838f2eb0f103a2b45c3a4d4403ea45 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmqrscp" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmqrscp" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmqrscp \- DICOM image archive (central test node)
@@ -731,6 +731,12 @@ BasicVoiceAudioWaveformStorage                       1.2.840.10008.5.1.4.1.1.9.4
 GeneralAudioWaveformStorage                          1.2.840.10008.5.1.4.1.1.9.4.2
 ArterialPulseWaveformStorage                         1.2.840.10008.5.1.4.1.1.9.5.1
 RespiratoryWaveformStorage                           1.2.840.10008.5.1.4.1.1.9.6.1
+MultichannelRespiratoryWaveformStorage               1.2.840.10008.5.1.4.1.1.9.6.2
+RoutineScalpElectroencephalogramWaveformStorage      1.2.840.10008.5.1.4.1.1.9.7.1
+ElectromyogramWaveformStorage                        1.2.840.10008.5.1.4.1.1.9.7.2
+ElectrooculogramWaveformStorage                      1.2.840.10008.5.1.4.1.1.9.7.3
+SleepElectroencephalogramWaveformStorage             1.2.840.10008.5.1.4.1.1.9.7.4
+BodyPositionWaveformStorage                          1.2.840.10008.5.1.4.1.1.9.8.1
 RETIRED_StandaloneModalityLUTStorage                 1.2.840.10008.5.1.4.1.1.10
 RETIRED_StandaloneVOILUTStorage                      1.2.840.10008.5.1.4.1.1.11
 GrayscaleSoftcopyPresentationStateStorage            1.2.840.10008.5.1.4.1.1.11.1
@@ -785,6 +791,7 @@ WideFieldOphthalmicPhotogr.3DCoordinatesImageStorage 1.2.840.10008.5.1.4.1.1.77.
 OphthalmicOpticalCoherenceTomogr.EnFaceImageStorage  1.2.840.10008.5.1.4.1.1.77.1.5.7
 OphthalmicOpticalCoh.Tomogr.BscanVolumeAnalysisStor. 1.2.840.10008.5.1.4.1.1.77.1.5.8
 VLWholeSlideMicroscopyImageStorage                   1.2.840.10008.5.1.4.1.1.77.1.6
+DermoscopicPhotographyImageStorage                   1.2.840.10008.5.1.4.1.1.77.1.7
 RETIRED_VLMultiframeImageStorage                     1.2.840.10008.5.1.4.1.1.77.2
 LensometryMeasurementsStorage                        1.2.840.10008.5.1.4.1.1.78.1
 AutorefractionMeasurementsStorage                    1.2.840.10008.5.1.4.1.1.78.2
@@ -824,6 +831,8 @@ ContentAssessmentResultsStorage                      1.2.840.10008.5.1.4.1.1.90.
 EncapsulatedPDFStorage                               1.2.840.10008.5.1.4.1.1.104.1
 EncapsulatedCDAStorage                               1.2.840.10008.5.1.4.1.1.104.2
 EncapsulatedSTLStorage                               1.2.840.10008.5.1.4.1.1.104.3
+EncapsulatedOBJStorage                               1.2.840.10008.5.1.4.1.1.104.4
+EncapsulatedMTLStorage                               1.2.840.10008.5.1.4.1.1.104.5
 PositronEmissionTomographyImageStorage               1.2.840.10008.5.1.4.1.1.128
 LegacyConvertedEnhancedPETImageStorage               1.2.840.10008.5.1.4.1.1.128.1
 RETIRED_StandalonePETCurveStorage                    1.2.840.10008.5.1.4.1.1.129
@@ -843,6 +852,13 @@ RTPhysicianIntentStorage                             1.2.840.10008.5.1.4.1.1.481
 RTSegmentAnnotationStorage                           1.2.840.10008.5.1.4.1.1.481.11
 RTRadiationSetStorage                                1.2.840.10008.5.1.4.1.1.481.12
 CArmPhotonElectronRadiationStorage                   1.2.840.10008.5.1.4.1.1.481.13
+TomotherapeuticRadiationStorage                      1.2.840.10008.5.1.4.1.1.481.14
+RoboticArmRadiationStorage                           1.2.840.10008.5.1.4.1.1.481.15
+RTRadiationRecordSetStorage                          1.2.840.10008.5.1.4.1.1.481.16
+RTRadiationSalvageRecordStorage                      1.2.840.10008.5.1.4.1.1.481.17
+TomotherapeuticRadiationRecordStorage                1.2.840.10008.5.1.4.1.1.481.18
+CArmPhotonElectronRadiationRecordStorage             1.2.840.10008.5.1.4.1.1.481.19
+RoboticRadiationRecordStorage                        1.2.840.10008.5.1.4.1.1.481.20
 DICOS_CTImageStorage                                 1.2.840.10008.5.1.4.1.1.501.1
 DICOS_DigitalXRayImageStorageForPresentation         1.2.840.10008.5.1.4.1.1.501.2.1
 DICOS_DigitalXRayImageStorageForProcessing           1.2.840.10008.5.1.4.1.1.501.2.2
@@ -996,4 +1012,4 @@ The default behavior should be preferred and the \fIDCMDICTPATH\fP environment v
 \fBdcmqridx\fP(1), \fBdcmqrti\fP(1)
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 1993-2019 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 1993-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index 146b723b8f69b66d17c385206c1e5918e7288f2e..057b77fb86b37133caf2df78c363d28ea58b78a0 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmqrti" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmqrti" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmqrti \- The Terminal Initiator Telnet Client Program
index 98e69f9a6a27de383151eaa5ab5d0c3fe1d04e97..6fb32214195f143007b764b909b7a1baadb91b57 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmquant" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmquant" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmquant \- Convert DICOM color images to palette color
index d004899f2858d84fd04c711007dc34329c3d89dd..3702e0d8586e457407ad54ad4c2b616fa0e75d5a 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmrecv" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmrecv" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmrecv \- Simple DICOM storage SCP (receiver)
@@ -84,6 +84,99 @@ other network options:
   -dhl  --disable-host-lookup  disable hostname lookup
 .fi
 .PP
+.SS "transport layer security (TLS) options"
+.PP
+.nf
+transport protocol stack:
+
+  -tls  --disable-tls
+          use normal TCP/IP connection (default)
+
+  +tls  --enable-tls  [p]rivate key file, [c]ertificate file: string
+          use authenticated secure TLS connection
+
+private key password (only with --enable-tls):
+
+  +ps   --std-passwd
+          prompt user to type password on stdin (default)
+
+  +pw   --use-passwd  [p]assword: string
+          use specified password
+
+  -pw   --null-passwd
+          use empty string as password
+
+key and certificate file format:
+
+  -pem  --pem-keys
+          read keys and certificates as PEM file (default)
+
+  -der  --der-keys
+          read keys and certificates as DER file
+
+certification authority:
+
+  +cf   --add-cert-file  [f]ilename: string
+          add certificate file to list of certificates
+
+  +cd   --add-cert-dir  [d]irectory: string
+          add certificates in d to list of certificates
+
+security profile:
+
+  +px   --profile-bcp195
+          BCP 195 TLS Profile (default)
+
+  +py   --profile-bcp195-nd
+          Non-downgrading BCP 195 TLS Profile
+
+  +pz   --profile-bcp195-ex
+          Extended BCP 195 TLS Profile
+
+  +pb   --profile-basic
+          Basic TLS Secure Transport Connection Profile (retired)
+
+  +pa   --profile-aes
+          AES TLS Secure Transport Connection Profile (retired)
+
+  +pn   --profile-null
+          Authenticated unencrypted communication
+          (retired, was used in IHE ATNA)
+
+ciphersuite:
+
+  +cc   --list-ciphers
+          show list of supported TLS ciphersuites and exit
+
+  +cs   --cipher  [c]iphersuite name: string
+          add ciphersuite to list of negotiated suites
+
+  +dp   --dhparam  [f]ilename: string
+          read DH parameters for DH/DSS ciphersuites
+
+pseudo random generator:
+
+  +rs   --seed  [f]ilename: string
+          seed random generator with contents of f
+
+  +ws   --write-seed
+          write back modified seed (only with --seed)
+
+  +wf   --write-seed-file  [f]ilename: string (only with --seed)
+          write modified seed to file f
+
+peer authentication:
+
+  -rc   --require-peer-cert
+          verify peer certificate, fail if absent (default)
+
+  -vc   --verify-peer-cert
+          verify peer certificate if present
+
+  -ic   --ignore-peer-cert
+          don't verify peer certificate
+.fi
+.PP
 .SS "output options"
 .PP
 .nf
@@ -264,6 +357,7 @@ EXITCODE_INVALID_OUTPUT_DIRECTORY        45
 EXITCODE_CANNOT_INITIALIZE_NETWORK       60 (*)
 EXITCODE_CANNOT_START_SCP_AND_LISTEN     64
 EXITCODE_INVALID_ASSOCIATION_CONFIG      66
+EXITCODE_CANNOT_CREATE_TRANSPORT_LAYER   71
 .fi
 .PP
 .PP
@@ -283,4 +377,4 @@ The default behavior should be preferred and the \fIDCMDICTPATH\fP environment v
 \fBdcmsend\fP(1), \fBstorescu\fP(1), \fBstorescp\fP(1)
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 2013-2017 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 2013-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index be9b53bda5da1f822302a467ef398831dbe7a6fe..1ce395f1e910a3f728e8dfcdef0adb0b60eb7035 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmscale" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmscale" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmscale \- Scale DICOM images
@@ -91,7 +91,7 @@ input transfer syntax:
 scaling:
 
   +a    --recognize-aspect
-          recognize pixel aspect ratio (default)
+          recognize pixel aspect ratio when scaling (default)
 
   -a    --ignore-aspect
           ignore pixel aspect ratio when scaling
@@ -230,4 +230,4 @@ The \fBdcmscale\fP utility will attempt to load DICOM data dictionaries specifie
 The default behavior should be preferred and the \fIDCMDICTPATH\fP environment variable only used when alternative data dictionaries are required\&. The \fIDCMDICTPATH\fP environment variable has the same format as the Unix shell \fIPATH\fP variable in that a colon (':') separates entries\&. On Windows systems, a semicolon (';') is used as a separator\&. The data dictionary code will attempt to load each file specified in the \fIDCMDICTPATH\fP environment variable\&. It is an error if no data dictionary can be loaded\&.
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 2002-2014 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 2002-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index 586d8e43252d27bae9fdb51a0b42df36a6e17948..496049b703165c376d2c923086c04802c126af94 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmsend" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmsend" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmsend \- Simple DICOM storage SCU (sender)
index f218466a0e0ba05836163b0f617dca5a8a770601..0e2e4cdfd934d7fd9188de2b874d18e55681c5eb 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcmsign" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcmsign" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcmsign \- Sign and Verify DICOM Files
@@ -98,6 +98,14 @@ input transfer syntax:
 
   -ti   --read-xfer-implicit
           read with implicit VR little endian TS
+
+handling of defined length UN elements:
+
+  -uc   --retain-un
+          retain elements as UN (default)
+
+  +uc   --convert-un
+          convert to real VR if known
 .fi
 .PP
 .SS "signature commands"
@@ -112,6 +120,10 @@ input transfer syntax:
   +si   --sign-item  [k]eyfile, [c]ertfile, [i]tem location: string
           create signature in sequence item
 
+  +t    --insert-timestamp  ts[q]file, ts[r]file [u]idfile: string
+          insert certified timestamp from ts response r
+          from timestamp query q at signature UID u
+
   +r    --remove  [s]ignature UID: string
           remove signature
 
@@ -119,7 +131,83 @@ input transfer syntax:
           remove all signatures from data set
 .fi
 .PP
-.SS "signature creation options (only with &ndash;sign or &ndash;sign-item):"
+.SS "general signature options"
+.PP
+.nf
+key and certificate file format:
+
+  -pem  --pem-keys
+          read keys/certificates as PEM file (default)
+
+  -der  --der-keys
+          read keys/certificates as DER file
+
+signature format:
+
+  -fn   --format-new
+          use correct DICOM signature format (default)
+
+  -fo   --format-old
+          use old (pre-3.5.4) DCMTK signature format, non-conformant
+          if signature includes compressed pixel data. This option should
+          only be used to verify signatures in the old format.
+.fi
+.PP
+.SS "signature verification options (only with &ndash;verify)"
+.PP
+.nf
+signature verification:
+
+  +rv   --verify-if-present
+          verify signatures if present, pass otherwise
+          (default)
+
+  +rg   --require-sig
+          fail if no signature at all is present
+
+  +rc   --require-creator
+          fail if no creator RSA signature is present
+
+  +ru   --require-auth
+          fail if no auth RSA signature is present
+
+  +rs   --require-sr
+          fail if no SR RSA signature is present
+
+timestamp verification:
+
+  +tv   --verify-ts
+          verify certified timestamp if present (default)
+
+  -tv   --ignore-ts
+          ignore certified timestamps
+
+  +tr   --require-ts
+          fail if no certified timestamp is present
+
+certification authority:
+
+  +cf   --add-cert-file
+          [f]ilename: string
+          add trusted certificate file to cert store
+
+  +uf   --add-ucert-file
+          [f]ilename: string
+          add untrusted intermediate certificate file
+
+  +cd   --add-cert-dir
+          [d]irectory: string
+          add certificates in d to cert store
+
+  +cr   --add-crl-file
+          [f]ilename: string
+          add certificate revocation list file
+          (implies --enable-crl-vfy)
+
+  +cl   --enable-crl-vfy
+          enable certificate revocation list verification.fi
+.PP
+.SS "signature creation options (only with &ndash;sign or &ndash;sign-item)"
 .PP
 .nf
 private key password:
@@ -133,14 +221,6 @@ private key password:
   -pw   --null-passwd
           use empty string as password
 
-key and certificate file format:
-
-  -pem  --pem-keys
-          read keys/certificates as PEM file (default)
-
-  -der  --der-keys
-          read keys/certificates as DER file
-
 digital signature profile:
 
   -pf   --profile-none
@@ -155,6 +235,12 @@ digital signature profile:
   +pa   --profile-auth
           enforce authorization signature profile
 
+  +pr   --profile-sr
+          enforce SR RSA signature profile
+
+  +pv   --profile-srv
+          enforce SR RSA signature profile (verification)
+
 MAC algorithm:
 
   +mr   --mac-ripemd160
@@ -166,6 +252,27 @@ MAC algorithm:
   +mm   --mac-md5
           use MD 5
 
+  +m2   --mac-sha256
+          use SHA-256
+
+  +m3   --mac-sha384
+          use SHA-384
+
+  +m5   --mac-sha512
+          use SHA-512
+
+signature purpose:
+
+  +lp   --list-purposes
+          show list of signature purpose codes and exit
+
+  -sp   --no-sig-purpose
+          do not add signature purpose (default)
+
+  +sp   --sig-purpose
+          [p]urpose code: integer (1..18)
+          add digital signature purpose code p
+
 tag selection:
 
   -t    --tag
@@ -174,16 +281,62 @@ tag selection:
           (this option can be specified multiple times)
 
   -tf   --tag-file  [f]ilename: string
-          read list of tags from text file
+          read list of tags from text file.fi
+.PP
+.SS "timestamp creation options (only with &ndash;sign or &ndash;sign-item)"
+.PP
+.nf
+timestamp creation:
 
-signature format:
+  -ts   --timestamp-off
+          do not create timestamp (default)
 
-  -fn   --format-new
-          use correct DICOM signature format (default)
+  +ts   --timestamp-file  [t]sq-filename, [u]id-filename: string
+          create timestamp query file t and uid file u
 
-  -fo   --format-old
-          use old (pre-3.5.4) DCMTK signature format, non-conformant
-          if signature includes compressed pixel data
+timestamp MAC algorithm (only with --timestamp-file):
+
+  +tm2  --ts-mac-sha256
+          use SHA-256 (default)
+
+  +tm3  --ts-mac-sha384
+          use SHA-384
+
+  +tm5  --ts-mac-sha512
+          use SHA-512
+
+  +tmr  --ts-mac-ripemd160
+          use RIPEMD 160
+
+  +tms  --ts-mac-sha1
+          use SHA-1 (not recommended)
+
+  +tmm  --ts-mac-md5
+          use MD5 (not recommended)
+
+timestamp query nonce options (only with --timestamp-file):
+
+  +tn   --ts-use-nonce
+          include random nonce (default)
+
+  -tn   --ts-no-nonce
+          do not include nonce
+
+timestamp certificate inclusion options (only with --timestamp-file):
+
+  +tc   --ts-request-cert
+          request TSA certificate in timestamp (default)
+
+  -tc   --ts-no-cert
+          do not request TSA certificate in timestamp
+
+timestamp policy options (only with --timestamp-file):
+
+  -tp   --ts-no-policy
+          do not specify ts policy (default)
+
+  +tp   --ts-policy  [p]olicy-OID: string
+          request timestamp policy p
 .fi
 .PP
 .SS "output options"
@@ -223,13 +376,13 @@ other output options:
 .SS "Files and Parameters"
 The \fBdcmsign\fP utility reads and writes a number of files and file formats which are described in this section\&.
 .PP
-Public Key Certificates are expected in X\&.509v3 format, either with PEM or DER encoding\&. The dcmsign utility currently supports RSA and DSA public keys, although only RSA keys are defines in the Security Profiles of the DICOM standard\&.
+Public Key Certificates are expected in X\&.509v3 format, either with PEM or DER encoding\&. The \fBdcmsign\fP utility currently supports RSA and DSA public keys, although only RSA keys are defines in the Security Profiles of the DICOM standard\&.
 .PP
 Private Keys are expected in PEM or DER encoding\&. PEM is recommended (and default) because this allows one to keep private keys in encrypted form\&. Command line options control the behavior of \fBdcmsign\fP when an encrypted PEM key is opened (see above)\&. In general it is not recommended to specify the encryption password in the command line because the command line may be visible to other processes in the system, e\&.g\&. 'ps -ef'\&.
 .PP
-The list of data elements to sign can either be read from a file or specified on the command line or both (in this case the keys are combined)\&.
+By default, \fBdcmsign\fP will create a signature covering all data elements in the dataset or item\&. This default can be overridden by explicitly specifying a list of data elements (attribute tags)\&. This list can either be read from a file or specified on the command line or both (in this case the attribute tags are combined)\&.
 .PP
-On the command line, attribute keys are specified as
+On the command line, attribute tags are specified as
 .PP
 .PP
 .nf
@@ -240,7 +393,9 @@ On the command line, attribute keys are specified as
 .fi
 .PP
 .PP
-When attribute tags are read from file with the \fI--tag-file\fP option, a plain text file of max\&. 64 kbyte is expected\&. Tags within the file are either symbolic names from the data dictionary or have the format (gggg,eeee) (with braces)\&. Tags are separated by one or more whitespace characters\&.
+When attribute tags are read from file with the \fI--tag-file\fP option, a plain text file is expected\&. Tags within the file are either symbolic names from the data dictionary or have the format (gggg,eeee) (with braces)\&. Tags are separated by one or more whitespace characters\&.
+.PP
+The currently selected digital signature profile may specify additional attribute tags required to be included in the signature, which will be silently added\&.
 .PP
 The \fI--sign-item\fP operation requires a location string that describes in which sequence item a signature is to be created\&. The location string has the following format:
 .PP
@@ -259,6 +414,20 @@ ReferencedSeriesSequence[0].ReferencedImageSequence[1]
 .PP
 .PP
 would cause a digital signature to be created in the second item of the ReferencedImageSequence (0008,1140) which is located in the first item of the ReferencedSeriesSequence (0008,1115) which is located in the main DICOM dataset\&.
+.SS "Certified Timestamps"
+Starting with release 3\&.6\&.6, \fBdcmsign\fP offers support for certified timestamps according to RFC 3161\&. For now, the tool does not implement any of the network protocols defined in RFC 3161 for communicating with a timestamp authority (TSA), but it can write a timestamp query (TSQ) during signature creation, and the new command \fI--insert-timestamp\fP will read a timestamp response (TSR) from file and add it to the DICOM digital signature\&. Since a DICOM file can contain multiple signatures, a 'UID file' (which contains the Digital Signature UID) is used to identify the signature to which the TSR should be added\&. The \fBdcmsign\fP tool will also perform various consistency checks before storing the timestamp\&.
+.PP
+During signature verification, the presence of a certified timestamp will be detected and the timestamp will also be verified unless option \fI--ignore-ts\fP was used\&. Signature verification and timestamp verification use a common certificate store to check the certificates of the DICOM signature and the timestamp\&. This store can be populated with the options \fI--add-cert-file\fP and \fI--add-cert-dir\fP, which both add trusted CA certificates, \fI--add-ucert-file\fP, which adds an untrusted intermediate CA certificate, and \fI--add-crl-file\fP, which adds a certificate revocation list\&.
+.SS "Hashed Certificate Directories"
+Instead of adding CA certificates and certificate revocation lists (CRLs) manually using \fI--add-cert-file\fP and \fI--add-crl-file\fP, the user can set-up a directory where \fBdcmsign\fP will look-up and load certificates and CRLs from as needed, using \fI--add-cert-dir\fP\&.
+.PP
+Th directory should contain one certificate or CRL per file in PEM format, with a filename of the form hash\&.N for a certificate, or hash\&.rN for a CRL\&. The hash is the value returned by
+.PP
+\fIopenssl x509 -hash -noout -in <filename\&.pem>\fP (for a certificate) \fIopenssl crl -hash -noout -in <filename\&.pem>\fP (for a CRL)
+.PP
+The \&.N or \&.rN suffix is a sequence number that starts at zero, and is incremented consecutively for each certificate or CRL with the same hash value\&. Gaps in the sequence numbers are not supported, it is assumed that there are no more objects with the same hash beyond the first missing number in the sequence\&.
+.PP
+CRLs will only be verified when option \fI--enable-crl-vfy\fP is specified\&. In this case, \fBdcmsign\fP will expect a CRL to be present for each CA and will fail signature verification if no CRL can be found for the CA that issued the signer certificate\&.
 .SH "LOGGING"
 .PP
 The level of logging output of the various command line tools and underlying libraries can be specified by the user\&. By default, only errors and warnings are written to the standard error stream\&. Using option \fI--verbose\fP also informational messages like processing details are reported\&. Option \fI--debug\fP can be used to get more details on the internal activity, e\&.g\&. for debugging purposes\&. Other logging levels can be selected using option \fI--log-level\fP\&. In \fI--quiet\fP mode only fatal errors are reported\&. In such very severe error events, the application will usually terminate\&. For more details on the different logging levels, see documentation of module 'oflog'\&.
@@ -271,6 +440,56 @@ All command line tools use the following notation for parameters: square bracket
 Command line options are distinguished from parameters by a leading '+' or '-' sign, respectively\&. Usually, order and position of command line options are arbitrary (i\&.e\&. they can appear anywhere)\&. However, if options are mutually exclusive the rightmost appearance is used\&. This behavior conforms to the standard evaluation rules of common Unix shells\&.
 .PP
 In addition, one or more command files can be specified using an '@' sign as a prefix to the filename (e\&.g\&. \fI@command\&.txt\fP)\&. Such a command argument is replaced by the content of the corresponding text file (multiple whitespaces are treated as a single separator unless they appear between two quotation marks) prior to any further evaluation\&. Please note that a command file cannot contain another command file\&. This simple but effective approach allows one to summarize common combinations of options/parameters and avoids longish and confusing command lines (an example is provided in file \fI<datadir>/dumppat\&.txt\fP)\&.
+.SH "EXIT CODES"
+.PP
+The \fBdcmsign\fP utility uses the following exit codes when terminating\&. This enables the user to check for the reason why the application terminated\&.
+.SS "general"
+.PP
+.nf
+EXITCODE_NO_ERROR                         0
+EXITCODE_COMMANDLINE_SYNTAX_ERROR         1
+EXITCODE_NOOPENSSL                        5
+.fi
+.PP
+.SS "input file errors"
+.PP
+.nf
+EXITCODE_CANNOT_READ_INPUT_FILE          20
+EXITCODE_NO_INPUT_FILES                  21
+EXITCODE_CANNOT_READ_TAG_FILE            30
+EXITCODE_CANNOT_READ_TSQ_FILE            31
+EXITCODE_CANNOT_READ_TSR_FILE            32
+EXITCODE_CANNOT_READ_UID_FILE            33
+.fi
+.PP
+.SS "output file errors"
+.PP
+.nf
+EXITCODE_CANNOT_WRITE_OUTPUT_FILE        40
+EXITCODE_CANNOT_WRITE_SUPPORT_FILE       46
+.fi
+.PP
+.SS "processing errors"
+.PP
+.nf
+EXITCODE_CANNOT_ACCESS_SIGNATURE         80
+EXITCODE_CANNOT_ACCESS_TS                81
+EXITCODE_CANNOT_INSERT_TS                82
+EXITCODE_SIGNATURE_REMOVAL_FAILED        83
+EXITCODE_SIGNATURE_UID_NOT_FOUND         84
+EXITCODE_SIGNATURE_CREATION_FAILED       85
+EXITCODE_SYNTAX_ERROR_IN_TAG_FILE        86
+EXITCODE_TS_CONSISTENCY_CHECK_FAILED     87
+.fi
+.PP
+.SS "application specific errors"
+.PP
+.nf
+EXITCODE_NO_SIGNATURES_PRESENT           100
+EXITCODE_SIGNATURE_VERIFICATION_FAILED   101
+EXITCODE_SIGNATURE_VERIFICATION_POLICY   102
+.fi
+.PP
 .SH "ENVIRONMENT"
 .PP
 The \fBdcmsign\fP utility will attempt to load DICOM data dictionaries specified in the \fIDCMDICTPATH\fP environment variable\&. By default, i\&.e\&. if the \fIDCMDICTPATH\fP environment variable is not set, the file \fI<datadir>/dicom\&.dic\fP will be loaded unless the dictionary is built into the application (default for Windows)\&.
@@ -278,4 +497,4 @@ The \fBdcmsign\fP utility will attempt to load DICOM data dictionaries specified
 The default behavior should be preferred and the \fIDCMDICTPATH\fP environment variable only used when alternative data dictionaries are required\&. The \fIDCMDICTPATH\fP environment variable has the same format as the Unix shell \fIPATH\fP variable in that a colon (':') separates entries\&. On Windows systems, a semicolon (';') is used as a separator\&. The data dictionary code will attempt to load each file specified in the \fIDCMDICTPATH\fP environment variable\&. It is an error if no data dictionary can be loaded\&.
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 2000-2014 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 2000-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index ad1777a6de6d9dd3c275584d0f24c57de1242e32..90adaa2e070a52728727d7e9e616f4ef1ec92d25 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dcod2lum" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dcod2lum" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dcod2lum \- Convert hardcopy characteristic curve file to softcopy format
index 7c5e3f22dd27efcea66502ed9cb6999de23ea482..2f5f8752e9853fe2816512bc5cdd89b3c7ee88ed 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dconvlum" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dconvlum" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dconvlum \- Convert VeriLUM files to DCMTK display files
index dba43015c0415c4efc5119a09e24cdabcc546e41..952fc70340cb75cf02cb0e2a380c43b2487bc292 100644 (file)
@@ -1,4 +1,4 @@
-.TH "drtdump" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "drtdump" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 drtdump \- Dump DICOM RT file and data set
index 256293476b3c478cca8abfb2dc785bfa490cf457..7735cd91f776fa0cf99c62de7b260d9af23a2ff3 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dsr2html" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dsr2html" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dsr2html \- Render DICOM SR file and data set to HTML/XHTML
index 78e231426269427fdc0d2a31d1d1907ee5d066ed..7ca5f25b18c02bd8c2fae7ee10c6f3e578f2f494 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dsr2xml" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dsr2xml" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dsr2xml \- Convert DICOM SR file and data set to XML
index af537c33f7599310bfe8fb2941d3bc526af297ed..7b8817d6870087c5783694674a94337d686098f1 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dsrdump" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dsrdump" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dsrdump \- Dump DICOM SR file and data set
index a36c4ad323e2b20a0fbdb68d5617a4881f6d13aa..a2903e18b6e52ba43fd9c66a0e30b6acb4ab5815 100644 (file)
@@ -1,4 +1,4 @@
-.TH "dump2dcm" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "dump2dcm" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 dump2dcm \- Convert ASCII dump to DICOM file
@@ -195,13 +195,13 @@ VR:    Value Representation must be written as 2 characters as in
        between the two characters.  If the VR can be determined from
        the tag, this part of a line is optional.
 Value: There are several rules for writing values:
-       1. US, SS, SL, UL, FD, FL, OD, OF and OL are written as decimal
-          strings that can be read by scanf().
+       1. US, SS, UL, SL, UV, SV, FD, FL, OD, OF, OL and OV are written
+          as decimal strings that can be read by scanf().
        2. AT is written as '(gggg,eeee)' with additional spaces
           stripped off automatically and gggg and eeee being decimal
           strings that can be read by scanf().
        3. OB and OW values are written as byte or word hexadecimal
-          values separated by '\\' character.  Alternatively, OB or OW
+          values separated by '\' character.  Alternatively, OB or OW
           values can be read from a separate file by writing the
           filename prefixed by a '=' character (e.g. '=largepix.dat').
           The contents of the file will be read as is.  By default, OW
@@ -221,22 +221,24 @@ Value: There are several rules for writing values:
           line.  Anything after the ']' is interpreted as comment.
        7. '(' and '<' are interpreted special and may not be used when
           writing an input file by hand as beginning characters of a
-          string.  Multiple Value are separated by '\\'.  The lines
+          string.  Multiple Value are separated by '\'.  The lines
           need not be sorted into ascending tag order.  References in
           DICOM Directories are not supported.  Semantic errors are
           not detected.
 .fi
 .PP
-.SS "Example"
+.SS "Examples"
+The following lines show valid examples of the syntax described above:
+.PP
 .PP
 .nf
  (0008,0020) DA [19921012]            #  8, 1 StudyDate
  (0008,0016) UI =MRImageStorage       # 26, 1 SOPClassUID
  (0002,0012) UI [1.2.276.0.7230010.100.1.1]
- (0020,0032) DS [0.0\\0.0]             #  8, 2 ImagePositionPatient
+ (0020,0032) DS [0.0\0.0]             #  8, 2 ImagePositionPatient
  (0028,0009) AT (3004,000c)           #  4, 1 FrameIncrementPointer
  (0028,0010) US 256                   #  4, 1 Rows
- (0002,0001) OB 01\\00
+ (0002,0001) OB 01\00
 .fi
 .PP
 .SS "Limitations"
@@ -263,4 +265,4 @@ The default behavior should be preferred and the \fIDCMDICTPATH\fP environment v
 \fBdcmdump\fP(1)
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 1996-2016 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 1996-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index e7445acd10f9db5fbf9286848f0cd97b3c21f214..2125ad970aeb132e6abcaa7523d99ffff3e3db31 100644 (file)
@@ -1,4 +1,4 @@
-.TH "echoscu" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "echoscu" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 echoscu \- DICOM verification (C-ECHO) SCU
@@ -131,10 +131,10 @@ key and certificate file format:
 
 certification authority:
 
-  +cf   --add-cert-file  [c]ertificate filename: string
+  +cf   --add-cert-file  [f]ilename: string
           add certificate file to list of certificates
 
-  +cd   --add-cert-dir  [c]ertificate directory: string
+  +cd   --add-cert-dir  [d]irectory: string
           add certificates in d to list of certificates
 
 security profile:
@@ -254,4 +254,4 @@ The \fBechoscu\fP utility will attempt to load DICOM data dictionaries specified
 The default behavior should be preferred and the \fIDCMDICTPATH\fP environment variable only used when alternative data dictionaries are required\&. The \fIDCMDICTPATH\fP environment variable has the same format as the Unix shell \fIPATH\fP variable in that a colon (':') separates entries\&. On Windows systems, a semicolon (';') is used as a separator\&. The data dictionary code will attempt to load each file specified in the \fIDCMDICTPATH\fP environment variable\&. It is an error if no data dictionary can be loaded\&.
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 1994-2018 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 1994-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index 6a33dd57fb5496ef838c1b0f29bae61fc20c90d6..293165df2eda23f79f8cb677746ed54dcbb7e969 100644 (file)
@@ -1,4 +1,4 @@
-.TH "findscu" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "findscu" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 findscu \- DICOM query (C-FIND) SCU
@@ -124,6 +124,9 @@ other network options:
   -to   --timeout  [s]econds: integer (default: unlimited)
           timeout for connection requests
 
+  -ts   --socket-timeout  [s]econds: integer (default: 60)
+          timeout for network socket (0 for none)
+
   -ta   --acse-timeout  [s]econds: integer (default: 30)
           timeout for ACSE messages
 
@@ -178,10 +181,10 @@ key and certificate file format:
 
 certification authority:
 
-  +cf   --add-cert-file  [c]ertificate filename: string
+  +cf   --add-cert-file  [f]ilename: string
           add certificate file to list of certificates
 
-  +cd   --add-cert-dir  [c]ertificate directory: string
+  +cd   --add-cert-dir  [d]irectory: string
           add certificates in d to list of certificates
 
 security profile:
@@ -265,6 +268,10 @@ C-FIND responses:
 
   -Xs   --extract-xml-single  [f]ilename: string
           extract all responses to given XML file f
+
+  -Xlo  --limit-output  [n]umber: integer
+          limit number of responses extracted to file to n
+          (default: unlimited)
 .fi
 .PP
 .SH "NOTES"
@@ -371,4 +378,4 @@ The default behavior should be preferred and the \fIDCMDICTPATH\fP environment v
 \fBmovescu\fP(1), \fBdump2dcm\fP(1), \fBdcmodify\fP(1)
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 1994-2019 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 1994-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index b26f825d595231e922ca60579abc55d1e108564f..cad0d80c2b12b48380fe88305c35c6de57fdeec5 100644 (file)
@@ -1,4 +1,4 @@
-.TH "getscu" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "getscu" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 getscu \- DICOM retrieve (C-GET) SCU
index 08908565cbb0e63e6bc19ec12dcb19cbe63540a6..8ffc2e0b8d595e7899567e79b06fcc3aa2a698e2 100644 (file)
@@ -1,4 +1,4 @@
-.TH "img2dcm" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "img2dcm" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 img2dcm \- Convert standard image formats into DICOM format
@@ -225,7 +225,7 @@ With the \fI--insert-type2\fP and \fI--invent-type1\fP options (both enabled per
 .PP
 .PD 0
 .IP "\(bu" 2
-The \fI--key\fP option can be used to add further attributes to the DICOM output file\&. This option is applied at the very end, just before saving the DICOM file\&. It is also possible to specify sequences, items and nested attributes using the \fI--key\fP option\&. In these cases, a special 'path' notation has to be used\&. Details on this path notation can be found in the documentation of \fBdcmodify\fP\&.
+The \fI--key\fP option can be used to add further attributes to the DICOM output file\&. It is also possible to specify sequences, items and nested attributes using the \fI--key\fP option\&. In these cases, a special 'path' notation has to be used\&. Details on this path notation can be found in the documentation of \fBdcmodify\fP\&. The \fI--key\fP option can be present more than once\&. The value part (after the '=') may be absent causing the attribute to be set with zero length\&. Please be advised that the \fI--key\fP option is applied at the very end, just before saving the DICOM file, so there is no value checking whatsoever\&.
 .PP
 .SS "UIDs"
 New Study and Series Instance UIDs are generated \fBif necessary\fP after applying the \fI--study-from\fP and \fI--series\fP options\&. If Study Instance UID or Series Instance UID are not present after these steps, they are newly generated, independently from each other\&. A contrary behavior is chosen for the SOP Instance UID that one could expect to be taken over when using the \fI--dataset-from\fP option\&. This is \fBnot\fP the case, the SOP Instance UID is \fBnot\fP copied to the new object\&. This should be the desirable behavior for most use cases\&. However, if a certain SOP Instance UID should be inserted into the new object, the \fI--key\fP option should be used\&.
@@ -346,4 +346,4 @@ The default behavior should be preferred and the \fIDCMDICTPATH\fP environment v
 \fBdcm2pnm\fP(1), \fBdcmj2pnm\fP(1), \fBdump2dcm\fP(1), \fBdcmconv\fP(1), \fBdcmodify\fP(1)
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 2007-2019 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 2007-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index 35ce957b53124ab9ae7937bd9d6e6dfe558deba5..752ef9b80896c74287de3631ba4f94f22b77682c 100644 (file)
@@ -1,4 +1,4 @@
-.TH "movescu" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "movescu" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 movescu \- DICOM retrieve (C-MOVE) SCU
@@ -436,6 +436,12 @@ BasicVoiceAudioWaveformStorage                       1.2.840.10008.5.1.4.1.1.9.4
 GeneralAudioWaveformStorage                          1.2.840.10008.5.1.4.1.1.9.4.2
 ArterialPulseWaveformStorage                         1.2.840.10008.5.1.4.1.1.9.5.1
 RespiratoryWaveformStorage                           1.2.840.10008.5.1.4.1.1.9.6.1
+MultichannelRespiratoryWaveformStorage               1.2.840.10008.5.1.4.1.1.9.6.2
+RoutineScalpElectroencephalogramWaveformStorage      1.2.840.10008.5.1.4.1.1.9.7.1
+ElectromyogramWaveformStorage                        1.2.840.10008.5.1.4.1.1.9.7.2
+ElectrooculogramWaveformStorage                      1.2.840.10008.5.1.4.1.1.9.7.3
+SleepElectroencephalogramWaveformStorage             1.2.840.10008.5.1.4.1.1.9.7.4
+BodyPositionWaveformStorage                          1.2.840.10008.5.1.4.1.1.9.8.1
 RETIRED_StandaloneModalityLUTStorage                 1.2.840.10008.5.1.4.1.1.10
 RETIRED_StandaloneVOILUTStorage                      1.2.840.10008.5.1.4.1.1.11
 GrayscaleSoftcopyPresentationStateStorage            1.2.840.10008.5.1.4.1.1.11.1
@@ -490,6 +496,7 @@ WideFieldOphthalmicPhotogr.3DCoordinatesImageStorage 1.2.840.10008.5.1.4.1.1.77.
 OphthalmicOpticalCoherenceTomogr.EnFaceImageStorage  1.2.840.10008.5.1.4.1.1.77.1.5.7
 OphthalmicOpticalCoh.Tomogr.BscanVolumeAnalysisStor. 1.2.840.10008.5.1.4.1.1.77.1.5.8
 VLWholeSlideMicroscopyImageStorage                   1.2.840.10008.5.1.4.1.1.77.1.6
+DermoscopicPhotographyImageStorage                   1.2.840.10008.5.1.4.1.1.77.1.7
 RETIRED_VLMultiframeImageStorage                     1.2.840.10008.5.1.4.1.1.77.2
 LensometryMeasurementsStorage                        1.2.840.10008.5.1.4.1.1.78.1
 AutorefractionMeasurementsStorage                    1.2.840.10008.5.1.4.1.1.78.2
@@ -529,6 +536,8 @@ ContentAssessmentResultsStorage                      1.2.840.10008.5.1.4.1.1.90.
 EncapsulatedPDFStorage                               1.2.840.10008.5.1.4.1.1.104.1
 EncapsulatedCDAStorage                               1.2.840.10008.5.1.4.1.1.104.2
 EncapsulatedSTLStorage                               1.2.840.10008.5.1.4.1.1.104.3
+EncapsulatedOBJStorage                               1.2.840.10008.5.1.4.1.1.104.4
+EncapsulatedMTLStorage                               1.2.840.10008.5.1.4.1.1.104.5
 PositronEmissionTomographyImageStorage               1.2.840.10008.5.1.4.1.1.128
 LegacyConvertedEnhancedPETImageStorage               1.2.840.10008.5.1.4.1.1.128.1
 RETIRED_StandalonePETCurveStorage                    1.2.840.10008.5.1.4.1.1.129
@@ -548,6 +557,13 @@ RTPhysicianIntentStorage                             1.2.840.10008.5.1.4.1.1.481
 RTSegmentAnnotationStorage                           1.2.840.10008.5.1.4.1.1.481.11
 RTRadiationSetStorage                                1.2.840.10008.5.1.4.1.1.481.12
 CArmPhotonElectronRadiationStorage                   1.2.840.10008.5.1.4.1.1.481.13
+TomotherapeuticRadiationStorage                      1.2.840.10008.5.1.4.1.1.481.14
+RoboticArmRadiationStorage                           1.2.840.10008.5.1.4.1.1.481.15
+RTRadiationRecordSetStorage                          1.2.840.10008.5.1.4.1.1.481.16
+RTRadiationSalvageRecordStorage                      1.2.840.10008.5.1.4.1.1.481.17
+TomotherapeuticRadiationRecordStorage                1.2.840.10008.5.1.4.1.1.481.18
+CArmPhotonElectronRadiationRecordStorage             1.2.840.10008.5.1.4.1.1.481.19
+RoboticRadiationRecordStorage                        1.2.840.10008.5.1.4.1.1.481.20
 DICOS_CTImageStorage                                 1.2.840.10008.5.1.4.1.1.501.1
 DICOS_DigitalXRayImageStorageForPresentation         1.2.840.10008.5.1.4.1.1.501.2.1
 DICOS_DigitalXRayImageStorageForProcessing           1.2.840.10008.5.1.4.1.1.501.2.2
@@ -670,4 +686,4 @@ The default behavior should be preferred and the \fIDCMDICTPATH\fP environment v
 \fBfindscu\fP(1), \fBstorescp\fP(1), \fBdump2dcm\fP(1)
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 1994-2019 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 1994-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index 9459d2ad1ce49e37fcbfff2b811aad5217434161..cd3bd5002e2662398c0e29530de6259b9e908d33 100644 (file)
@@ -1,4 +1,4 @@
-.TH "pdf2dcm" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "pdf2dcm" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 pdf2dcm \- Encapsulate PDF file into DICOM file format
@@ -159,6 +159,31 @@ data set trailing padding (not with --write-dataset):
          and items on multiple of i bytes
 .fi
 .PP
+.SH "NOTES"
+.PP
+.SS "Attribute Sources"
+The application may be fed with some additional input for filling mandatory (and optional) attributes in the new DICOM file like patient, study and series information:
+.PP
+.PD 0
+.IP "\(bu" 2
+The \fI--key\fP option can be used to add further attributes to the DICOM output file\&.
+.PP
+.PD 0
+.IP "\(bu" 2
+It is also possible to specify sequences, items and nested attributes using the \fI--key\fP option\&. In these cases, a special 'path' notation has to be used\&. Details on this path notation can be found in the documentation of \fBdcmodify\fP\&.
+.PP
+.PD 0
+.IP "\(bu" 2
+The \fI--key\fP option can be present more than once\&.
+.PP
+.PD 0
+.IP "\(bu" 2
+The value part (after the '=') may be absent causing the attribute to be set with zero length\&.
+.PP
+.PD 0
+.IP "\(bu" 2
+Please be advised that the \fI--key\fP option is applied at the very end, just before saving the DICOM file, so there is no value checking whatsoever\&.
+.PP
 .SH "LOGGING"
 .PP
 The level of logging output of the various command line tools and underlying libraries can be specified by the user\&. By default, only errors and warnings are written to the standard error stream\&. Using option \fI--verbose\fP also informational messages like processing details are reported\&. Option \fI--debug\fP can be used to get more details on the internal activity, e\&.g\&. for debugging purposes\&. Other logging levels can be selected using option \fI--log-level\fP\&. In \fI--quiet\fP mode only fatal errors are reported\&. In such very severe error events, the application will usually terminate\&. For more details on the different logging levels, see documentation of module 'oflog'\&.
@@ -206,4 +231,4 @@ The default behavior should be preferred and the \fIDCMDICTPATH\fP environment v
 \fBdcm2pdf\fP(1)
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 2005-2018 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 2005-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index eab5b86525f2eb28cefbbb76154190d64a1e1f45..5e00f4b5419ff23ff13844c46b360a5907263fd2 100644 (file)
@@ -1,4 +1,4 @@
-.TH "stl2dcm" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "stl2dcm" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 stl2dcm \- Encapsulate STL file into DICOM file format
@@ -179,6 +179,31 @@ data set trailing padding (not with --write-dataset):
          and items on multiple of i bytes
 .fi
 .PP
+.SH "NOTES"
+.PP
+.SS "Attribute Sources"
+The application may be fed with some additional input for filling mandatory (and optional) attributes in the new DICOM file like patient, study and series information:
+.PP
+.PD 0
+.IP "\(bu" 2
+The \fI--key\fP option can be used to add further attributes to the DICOM output file\&.
+.PP
+.PD 0
+.IP "\(bu" 2
+It is also possible to specify sequences, items and nested attributes using the \fI--key\fP option\&. In these cases, a special 'path' notation has to be used\&. Details on this path notation can be found in the documentation of \fBdcmodify\fP\&.
+.PP
+.PD 0
+.IP "\(bu" 2
+The \fI--key\fP option can be present more than once\&.
+.PP
+.PD 0
+.IP "\(bu" 2
+The value part (after the '=') may be absent causing the attribute to be set with zero length\&.
+.PP
+.PD 0
+.IP "\(bu" 2
+Please be advised that the \fI--key\fP option is applied at the very end, just before saving the DICOM file, so there is no value checking whatsoever\&.
+.PP
 .SH "LOGGING"
 .PP
 The level of logging output of the various command line tools and underlying libraries can be specified by the user\&. By default, only errors and warnings are written to the standard error stream\&. Using option \fI--verbose\fP also informational messages like processing details are reported\&. Option \fI--debug\fP can be used to get more details on the internal activity, e\&.g\&. for debugging purposes\&. Other logging levels can be selected using option \fI--log-level\fP\&. In \fI--quiet\fP mode only fatal errors are reported\&. In such very severe error events, the application will usually terminate\&. For more details on the different logging levels, see documentation of module 'oflog'\&.
@@ -223,4 +248,4 @@ The \fBstl2dcm\fP utility will attempt to load DICOM data dictionaries specified
 The default behavior should be preferred and the \fIDCMDICTPATH\fP environment variable only used when alternative data dictionaries are required\&. The \fIDCMDICTPATH\fP environment variable has the same format as the Unix shell \fIPATH\fP variable in that a colon (':') separates entries\&. On Windows systems, a semicolon (';') is used as a separator\&. The data dictionary code will attempt to load each file specified in the \fIDCMDICTPATH\fP environment variable\&. It is an error if no data dictionary can be loaded\&.
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 2018 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 2018-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index 34430af0aec17416623db0ffc5bd6faa61cb0845..b73b59c7e351c22e252a209c287f684639822faa 100644 (file)
@@ -1,4 +1,4 @@
-.TH "storescp" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "storescp" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 storescp \- DICOM storage (C-STORE) SCP
@@ -239,10 +239,10 @@ key and certificate file format:
 
 certification authority:
 
-  +cf   --add-cert-file  [c]ertificate filename: string
+  +cf   --add-cert-file  [f]ilename: string
           add certificate file to list of certificates
 
-  +cd   --add-cert-dir  [c]ertificate directory: string
+  +cd   --add-cert-dir  [d]irectory: string
           add certificates in d to list of certificates
 
 security profile:
@@ -379,6 +379,14 @@ data set trailing padding
           align file on multiple of f bytes and items on
           multiple of i bytes
 
+handling of defined length UN elements:
+
+  -uc   --retain-un
+          retain elements as UN (default)
+
+  +uc   --convert-un
+          convert to real VR if known
+
 deflate compression level (only with --write-xfer-deflated/same):
 
   +cl   --compression-level  [l]evel: integer (default: 6)
@@ -559,6 +567,12 @@ BasicVoiceAudioWaveformStorage                       1.2.840.10008.5.1.4.1.1.9.4
 GeneralAudioWaveformStorage                          1.2.840.10008.5.1.4.1.1.9.4.2
 ArterialPulseWaveformStorage                         1.2.840.10008.5.1.4.1.1.9.5.1
 RespiratoryWaveformStorage                           1.2.840.10008.5.1.4.1.1.9.6.1
+MultichannelRespiratoryWaveformStorage               1.2.840.10008.5.1.4.1.1.9.6.2
+RoutineScalpElectroencephalogramWaveformStorage      1.2.840.10008.5.1.4.1.1.9.7.1
+ElectromyogramWaveformStorage                        1.2.840.10008.5.1.4.1.1.9.7.2
+ElectrooculogramWaveformStorage                      1.2.840.10008.5.1.4.1.1.9.7.3
+SleepElectroencephalogramWaveformStorage             1.2.840.10008.5.1.4.1.1.9.7.4
+BodyPositionWaveformStorage                          1.2.840.10008.5.1.4.1.1.9.8.1
 RETIRED_StandaloneModalityLUTStorage                 1.2.840.10008.5.1.4.1.1.10
 RETIRED_StandaloneVOILUTStorage                      1.2.840.10008.5.1.4.1.1.11
 GrayscaleSoftcopyPresentationStateStorage            1.2.840.10008.5.1.4.1.1.11.1
@@ -613,6 +627,7 @@ WideFieldOphthalmicPhotogr.3DCoordinatesImageStorage 1.2.840.10008.5.1.4.1.1.77.
 OphthalmicOpticalCoherenceTomogr.EnFaceImageStorage  1.2.840.10008.5.1.4.1.1.77.1.5.7
 OphthalmicOpticalCoh.Tomogr.BscanVolumeAnalysisStor. 1.2.840.10008.5.1.4.1.1.77.1.5.8
 VLWholeSlideMicroscopyImageStorage                   1.2.840.10008.5.1.4.1.1.77.1.6
+DermoscopicPhotographyImageStorage                   1.2.840.10008.5.1.4.1.1.77.1.7
 RETIRED_VLMultiframeImageStorage                     1.2.840.10008.5.1.4.1.1.77.2
 LensometryMeasurementsStorage                        1.2.840.10008.5.1.4.1.1.78.1
 AutorefractionMeasurementsStorage                    1.2.840.10008.5.1.4.1.1.78.2
@@ -652,6 +667,8 @@ ContentAssessmentResultsStorage                      1.2.840.10008.5.1.4.1.1.90.
 EncapsulatedPDFStorage                               1.2.840.10008.5.1.4.1.1.104.1
 EncapsulatedCDAStorage                               1.2.840.10008.5.1.4.1.1.104.2
 EncapsulatedSTLStorage                               1.2.840.10008.5.1.4.1.1.104.3
+EncapsulatedOBJStorage                               1.2.840.10008.5.1.4.1.1.104.4
+EncapsulatedMTLStorage                               1.2.840.10008.5.1.4.1.1.104.5
 PositronEmissionTomographyImageStorage               1.2.840.10008.5.1.4.1.1.128
 LegacyConvertedEnhancedPETImageStorage               1.2.840.10008.5.1.4.1.1.128.1
 RETIRED_StandalonePETCurveStorage                    1.2.840.10008.5.1.4.1.1.129
@@ -671,6 +688,13 @@ RTPhysicianIntentStorage                             1.2.840.10008.5.1.4.1.1.481
 RTSegmentAnnotationStorage                           1.2.840.10008.5.1.4.1.1.481.11
 RTRadiationSetStorage                                1.2.840.10008.5.1.4.1.1.481.12
 CArmPhotonElectronRadiationStorage                   1.2.840.10008.5.1.4.1.1.481.13
+TomotherapeuticRadiationStorage                      1.2.840.10008.5.1.4.1.1.481.14
+RoboticArmRadiationStorage                           1.2.840.10008.5.1.4.1.1.481.15
+RTRadiationRecordSetStorage                          1.2.840.10008.5.1.4.1.1.481.16
+RTRadiationSalvageRecordStorage                      1.2.840.10008.5.1.4.1.1.481.17
+TomotherapeuticRadiationRecordStorage                1.2.840.10008.5.1.4.1.1.481.18
+CArmPhotonElectronRadiationRecordStorage             1.2.840.10008.5.1.4.1.1.481.19
+RoboticRadiationRecordStorage                        1.2.840.10008.5.1.4.1.1.481.20
 DICOS_CTImageStorage                                 1.2.840.10008.5.1.4.1.1.501.1
 DICOS_DigitalXRayImageStorageForPresentation         1.2.840.10008.5.1.4.1.1.501.2.1
 DICOS_DigitalXRayImageStorageForProcessing           1.2.840.10008.5.1.4.1.1.501.2.2
@@ -771,4 +795,4 @@ The default behavior should be preferred and the \fIDCMDICTPATH\fP environment v
 \fBstorescu\fP(1)
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 1996-2019 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 1996-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index 64d9698b1404f299f5c7f4689c83ff44751a4f01..ea845f84661e886a555d4a4bcd7fb1070dc70d2d 100644 (file)
@@ -1,4 +1,4 @@
-.TH "storescu" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "storescu" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 storescu \- DICOM storage (C-STORE) SCU
@@ -321,10 +321,10 @@ key and certificate file format:
 
 certification authority:
 
-  +cf   --add-cert-file  [c]ertificate filename: string
+  +cf   --add-cert-file  [f]ilename: string
           add certificate file to list of certificates
 
-  +cd   --add-cert-dir  [c]ertificate directory: string
+  +cd   --add-cert-dir  [d]irectory: string
           add certificates in d to list of certificates
 
 security profile:
@@ -513,4 +513,4 @@ The default behavior should be preferred and the \fIDCMDICTPATH\fP environment v
 \fBstorescp\fP(1)
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 1996-2019 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 1996-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index 5b132adf5743a0740c9aed4e9ef19ce68fc24e9a..99cf267f11997a83d99eb6a4d2d4a0cce3e8ac26 100644 (file)
@@ -1,4 +1,4 @@
-.TH "termscu" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "termscu" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 termscu \- DICOM termination SCU
index a71209311a1cc4b1547bb127e5a9621d1f28d48a..3ae084988975b5c1de8d5dbfff485cca452cd376 100644 (file)
@@ -1,4 +1,4 @@
-.TH "wlmscpfs" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "wlmscpfs" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 wlmscpfs \- DICOM Basic Worklist Management SCP (based on data files)
@@ -97,12 +97,6 @@ other processing options:
   -nse  --no-sq-expansion
           disable expansion of empty sequences in C-FIND
           request messages
-
-  -rfp  --request-file-path  [p]ath: string
-          path to store request files to
-
-  -rff  --request-file-format  [f]ormat: string (default: #t.dump)
-          request file name format
 .fi
 .PP
 .SS "network options"
@@ -182,6 +176,18 @@ other network options:
           disable hostname lookup
 .fi
 .PP
+.SS "output options"
+.PP
+.nf
+general:
+
+  -rfp  --request-file-path  [p]ath: string
+          path to store request files to
+
+  -rff  --request-file-format  [f]ormat: string (default: #t.dump)
+          request file name format
+.fi
+.PP
 .SH "NOTES"
 .PP
 The semantic impacts of the above mentioned options is clear for the majority of options\&. Some particular options, however, are so specific that they need detailed descriptions which will be given in this passage\&.
@@ -413,4 +419,4 @@ The \fBwlmscpfs\fP utility will attempt to load DICOM data dictionaries specifie
 The default behavior should be preferred and the \fIDCMDICTPATH\fP environment variable only used when alternative data dictionaries are required\&. The \fIDCMDICTPATH\fP environment variable has the same format as the Unix shell \fIPATH\fP variable in that a colon (':') separates entries\&. On Windows systems, a semicolon (';') is used as a separator\&. The data dictionary code will attempt to load each file specified in the \fIDCMDICTPATH\fP environment variable\&. It is an error if no data dictionary can be loaded\&.
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 1996-2019 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 1996-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index 944114f0078914f3c5c832ec0003f16197c3b0e3..a1c2974c8c89130564c498d5c4b80e4b13698c74 100644 (file)
@@ -1,4 +1,4 @@
-.TH "xml2dcm" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "xml2dcm" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 xml2dcm \- Convert XML document to DICOM file or data set
@@ -194,7 +194,7 @@ The basic structure of the XML input expected looks like the following:
       <item card="3">
         <element tag="0028,3002" vr="xs" vm="3" len="6"
                  name="LUTDescriptor">
-          256\\0\\8
+          256\0\8
         </element>
         ...
       </item>
@@ -275,4 +275,4 @@ The default behavior should be preferred and the \fIDCMDICTPATH\fP environment v
 \fBdcm2xml\fP(1)
 .SH "COPYRIGHT"
 .PP
-Copyright (C) 2003-2019 by OFFIS e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
+Copyright (C) 2003-2021 e\&.V\&., Escherweg 2, 26121 Oldenburg, Germany\&.
index 1b008c35e76bf5f9e45a9e42b4a069d188ea0d94..79d5a61458bbe6285d5e57682cb7861a2aa3bf3c 100644 (file)
@@ -1,4 +1,4 @@
-.TH "xml2dsr" 1 "Mon Oct 28 2019" "Version 3.6.5" "OFFIS DCMTK" \" -*- nroff -*-
+.TH "xml2dsr" 1 "Thu Jan 14 2021" "Version 3.6.6" "OFFIS DCMTK" \" -*- nroff -*-
 .nh
 .SH NAME
 xml2dsr \- Convert XML document to DICOM SR file
index 9508dd00db3763162f03913eaf3372c5a180a0a3..c8dba6bce425489bab3f227f401924046458afce 100644 (file)
@@ -54,13 +54,13 @@ typedef int loglevel_t;
 #define L4CP_ALL_LOG_LEVEL TRACE_LOG_LEVEL
 #define L4CP_NOT_SET_LOG_LEVEL -1
 
-#ifdef UNICODE
+#ifdef DCMTK_OFLOG_UNICODE
 #  define DCMTK_LOG4CPLUS_TEXT2(STRING) L##STRING
 typedef wchar_t log4cplus_char_t;
 #else
 #  define DCMTK_LOG4CPLUS_TEXT2(STRING) STRING
 typedef char log4cplus_char_t;
-#endif // UNICODE
+#endif // DCMTK_OFLOG_UNICODE
 #define DCMTK_LOG4CPLUS_TEXT(STRING) DCMTK_LOG4CPLUS_TEXT2(STRING)
 
 DCMTK_LOG4CPLUS_EXPORT int log4cplus_file_configure(const log4cplus_char_t *pathname);
index 835e7d240c9d6b0010135e6324caf5312926d75a..8e21275c23d412d129cf967725ded8fcbdea5edc 100644 (file)
@@ -40,7 +40,7 @@
 #  include "dcmtk/oflog/config/defines.h"
 #endif
 
-#if ! defined (UNICODE) && ! defined (DCMTK_LOG4CPLUS_HAVE_VSNPRINTF_S) \
+#if ! defined (DCMTK_OFLOG_UNICODE) && ! defined (DCMTK_LOG4CPLUS_HAVE_VSNPRINTF_S) \
     && ! defined (DCMTK_LOG4CPLUS_HAVE__VSNPRINTF_S) \
     && ! defined (DCMTK_LOG4CPLUS_HAVE_VSNPRINTF) \
     && ! defined (DCMTK_LOG4CPLUS_HAVE__VSNPRINTF)
@@ -90,7 +90,7 @@
 #  define DCMTK_LOG4CPLUS_INLINE_EXPORT
 #endif
 
-#if defined (UNICODE)
+#if defined (DCMTK_OFLOG_UNICODE)
 #  if defined (_MSC_VER) && _MSC_VER >= 1400
 #    define DCMTK_LOG4CPLUS_FSTREAM_ACCEPTS_WCHAR_T
 #  endif
 #  define DCMTK_LOG4CPLUS_HAVE_RVALUE_REFS
 #endif
 
-#if ! defined (UNICODE) && defined (__GNUC__) && __GNUC__ >= 3
+#if ! defined (DCMTK_OFLOG_UNICODE) && defined (__GNUC__) && __GNUC__ >= 3
 #  define DCMTK_LOG4CPLUS_FORMAT_ATTRIBUTE(archetype, format_index, first_arg_index) \
     __attribute__ ((format (archetype, format_index, first_arg_index)))
 #else
index e155c8b3ef91cd19ecc703a96111a0305a4d0a82..049569790a2ff7fea340108bca3187cd81a71153 100644 (file)
@@ -77,14 +77,14 @@ namespace log4cplus
             , fEncodingShift      = 3
             , fEncodingMask       = 0x3
             , fUnspecEncoding     = (0 << fEncodingShift)
-#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF8_FACET) && defined (UNICODE)
+#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF8_FACET) && defined (DCMTK_OFLOG_UNICODE)
             , fUTF8               = (1 << fEncodingShift)
 #endif
 #if (defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF16_FACET) || defined (_WIN32)) \
-    && defined (UNICODE)
+    && defined (DCMTK_OFLOG_UNICODE)
             , fUTF16              = (2 << fEncodingShift)
 #endif
-#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF32_FACET) && defined (UNICODE)
+#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF32_FACET) && defined (DCMTK_OFLOG_UNICODE)
             , fUTF32              = (3 << fEncodingShift)
 #endif
         };
index 7b30bc1880d766858a41a0abcef28e881c478ad5..136a531d734805c08b63e09ecec2c586c622e857 100644 (file)
@@ -46,7 +46,7 @@ typedef STD_NAMESPACE basic_ifstream<tchar> tifstream;
 //! \def DCMTK_LOG4CPLUS_FSTREAM_PREFERED_FILE_NAME(X)
 //! \brief Expands into expression that picks the right type for
 //! STD_NAMESPACE fstream file name parameter.
-#if defined (DCMTK_LOG4CPLUS_FSTREAM_ACCEPTS_WCHAR_T) && defined (UNICODE)
+#if defined (DCMTK_LOG4CPLUS_FSTREAM_ACCEPTS_WCHAR_T) && defined (DCMTK_OFLOG_UNICODE)
 #  define DCMTK_LOG4CPLUS_FSTREAM_PREFERED_FILE_NAME(X) (X)
 #else
 #  define DCMTK_LOG4CPLUS_FSTREAM_PREFERED_FILE_NAME(X) (DCMTK_LOG4CPLUS_TSTRING_TO_STRING(X))
index 3e42c4c7a6098ed70713f0659b1ea16d2811f43e..7b0c941ed3c45a38e49cdec8163fef7aa1e8ef53 100644 (file)
@@ -51,14 +51,14 @@ namespace log4cplus {
                 fEncodingShift      = 3
                 , fEncodingMask     = 0x3
                 , fUnspecEncoding   = (0 << fEncodingShift)
-#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF8_FACET) && defined (UNICODE)
+#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF8_FACET) && defined (DCMTK_OFLOG_UNICODE)
                 , fUTF8             = (1 << fEncodingShift)
 #endif
 #if (defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF16_FACET) || defined (_WIN32)) \
-    && defined (UNICODE)
+    && defined (DCMTK_OFLOG_UNICODE)
                 , fUTF16            = (2 << fEncodingShift)
 #endif
-#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF32_FACET) && defined (UNICODE)
+#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF32_FACET) && defined (DCMTK_OFLOG_UNICODE)
                 , fUTF32            = (3 << fEncodingShift)
 #endif
             };
index 1ec0201d949920224aaa36ecbecce64b5c37f458..f256df38ddd2a62ebbf1a26335cc815572408dee 100644 (file)
@@ -121,7 +121,7 @@ public:
         //! ERROR_BIT signals error.
         ERROR_BIT   = 0x0010,
 
-        //! ERROR_AFTER signals error that has occured after queue has
+        //! ERROR_AFTER signals error that has occurred after queue has
         //! already been touched.
         ERROR_AFTER = 0x0020
     };
index c107782a606227bd45a855c54ead846420adaf73..9ec675e0db3fc736dc1c96ca0e53e00f6ca4a30b 100644 (file)
@@ -42,7 +42,7 @@ namespace log4cplus
 {
  
 
-#ifndef UNICODE
+#ifndef DCMTK_OFLOG_UNICODE
     size_t const DCMTK_LOG4CPLUS_MAX_MESSAGE_SIZE = 8*1024;
 #else
     size_t const DCMTK_LOG4CPLUS_MAX_MESSAGE_SIZE = 2*8*1024;
index 4f6c5fb1d3aaf0f50cd196a20f6a173c7b8e517f..9f161e5ef3d6556e8258c44b91cdffb72b0b860e 100644 (file)
@@ -49,7 +49,7 @@ namespace log4cplus
 }
 }
 
-#if defined (UNICODE) && defined (DCMTK_LOG4CPLUS_ENABLE_GLOBAL_C_STRING_STREAM_INSERTER)
+#if defined (DCMTK_OFLOG_UNICODE) && defined (DCMTK_LOG4CPLUS_ENABLE_GLOBAL_C_STRING_STREAM_INSERTER)
 
 DCMTK_LOG4CPLUS_EXPORT log4cplus::tostream& operator <<(log4cplus::tostream&, const char* psz );
 
index c3655d0e5628c2a8a1da57a75a632f294ae321cd..643d52aae02df8da3b3f72d94cb56dbc61a38046 100644 (file)
 #endif
 
 
-#ifdef UNICODE
+#ifdef DCMTK_OFLOG_UNICODE
 #  define DCMTK_LOG4CPLUS_TEXT2(STRING) L##STRING
 #else
 #  define DCMTK_LOG4CPLUS_TEXT2(STRING) STRING
-#endif // UNICODE
+#endif // DCMTK_OFLOG_UNICODE
 #define DCMTK_LOG4CPLUS_TEXT(STRING) DCMTK_LOG4CPLUS_TEXT2(STRING)
 
 
@@ -51,7 +51,7 @@ namespace dcmtk
 namespace log4cplus
 {
 
-#if defined (UNICODE)
+#if defined (DCMTK_OFLOG_UNICODE)
 typedef wchar_t tchar;
 
 #else
index 73718ad77357e3b1d3483fcbe9f9ea3220172380..4ebaf806e86f68fc0dd936729a2a1ce135f78974 100644 (file)
 
 #endif
 
+#ifdef __MINGW32__
+/* MinGW does not support fiber local storage. Use Thread Local Storage instead. */
+#define DCMTK_LOG4CPLUS_AVOID_WIN32_FLS
+#endif
 
 namespace dcmtk {
 namespace log4cplus { namespace thread { namespace impl {
 
 
 typedef void * tls_value_type;
-typedef void (* tls_init_cleanup_func_type)(void *);
 
 #ifdef DCMTK_LOG4CPLUS_USE_PTHREADS
 typedef pthread_key_t * tls_key_type;
+typedef void (* tls_init_cleanup_func_type)(void *);
 
 #elif defined (DCMTK_LOG4CPLUS_USE_WIN32_THREADS)
 typedef DWORD tls_key_type;
+typedef void (WINAPI * tls_init_cleanup_func_type)(void *);
 
 #elif defined (DCMTK_LOG4CPLUS_SINGLE_THREADED)
 typedef size_t tls_key_type;
+typedef void (* tls_init_cleanup_func_type)(void *);
 
 #endif
 
index 7ca173c44e4c47f0fdfa119f2fc3baba303de940..d1c56abd5c56b041a4c5f3cebbd47edefeb8289d 100644 (file)
@@ -83,19 +83,19 @@ DCMTK_LOG4CPLUS_EXPORT STD_NAMESPACE wstring towstring(char const *);
 
 } // namespace helpers
 
-#ifdef UNICODE
+#ifdef DCMTK_OFLOG_UNICODE
 
 #define DCMTK_LOG4CPLUS_C_STR_TO_TSTRING(STRING) log4cplus::helpers::towstring(STRING)
 #define DCMTK_LOG4CPLUS_STRING_TO_TSTRING(STRING) log4cplus::helpers::towstring(STRING)
 #define DCMTK_LOG4CPLUS_TSTRING_TO_STRING(STRING) log4cplus::helpers::tostring(STRING)
 
-#else // UNICODE
+#else // DCMTK_OFLOG_UNICODE
 
 #define DCMTK_LOG4CPLUS_C_STR_TO_TSTRING(STRING) OFString(STRING)
 #define DCMTK_LOG4CPLUS_STRING_TO_TSTRING(STRING) STRING
 #define DCMTK_LOG4CPLUS_TSTRING_TO_STRING(STRING) STRING
 
-#endif // UNICODE
+#endif // DCMTK_OFLOG_UNICODE
 
 } // namespace log4cplus
 } // end namespace dcmtk
index 689eb5a12f2881ce5fbbbd0a0c08f8e6142932f2..c755d39d1dc4d426360109aaef42c45cc6b8a1fa 100644 (file)
@@ -183,18 +183,18 @@ namespace
             & (PropertyConfigurator::fEncodingMask
                 << PropertyConfigurator::fEncodingShift))
         {
-#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF8_FACET) && defined (UNICODE)
+#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF8_FACET) && defined (DCMTK_OFLOG_UNICODE)
         case PropertyConfigurator::fUTF8:
             return helpers::Properties::fUTF8;
 #endif
 
 #if (defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF16_FACET) || defined (WIN32)) \
-    && defined (UNICODE)
+    && defined (DCMTK_OFLOG_UNICODE)
         case PropertyConfigurator::fUTF16:
             return helpers::Properties::fUTF16;
 #endif
 
-#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF32_FACET) && defined (UNICODE)
+#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF32_FACET) && defined (DCMTK_OFLOG_UNICODE)
         case PropertyConfigurator::fUTF32:
             return helpers::Properties::fUTF32;
 #endif
index d8ffd584c21b6ed629d93a5b88cd8a1cfd2c1abc..b6030edaadb9f0a92c35d606680db4a03dbb5203 100644 (file)
@@ -46,7 +46,7 @@ namespace log4cplus { namespace internal {
 bool
 get_env_var (tstring & value, tstring const & name)
 {
-#if defined (_WIN32) && defined (UNICODE)
+#if defined (_WIN32) && defined (DCMTK_OFLOG_UNICODE)
     tchar const * val = _wgetenv (name.c_str ());
     if (val)
         value = val;
index 1e3461590acae6585b67c7d0313b9d99451e2526..7c5a2ee755efc7c5c657bc80ab577c5c21baf33e 100644 (file)
@@ -77,7 +77,7 @@ static
 long
 file_rename (tstring const & src, tstring const & target)
 {
-#if defined (UNICODE) && defined (_WIN32)
+#if defined (DCMTK_OFLOG_UNICODE) && defined (_WIN32)
     if (_wrename (src.c_str (), target.c_str ()) == 0)
         return 0;
     else
@@ -98,7 +98,7 @@ static
 long
 file_remove (tstring const & src)
 {
-#if defined (UNICODE) && defined (_WIN32)
+#if defined (DCMTK_OFLOG_UNICODE) && defined (_WIN32)
     if (_wremove (src.c_str ()) == 0)
         return 0;
     else
index b8cd1893f40469fed680f88a3e885428e36fc923..cb225681c2133ddbaa729327a480f671c547e656 100644 (file)
@@ -48,8 +48,14 @@ getFileInfo (FileInfo * fi, tstring const & name)
 {
 #if defined (_WIN32)
     struct _stat fileStatus;
+
+#if defined (DCMTK_OFLOG_UNICODE)
     if (_tstat (name.c_str (), &fileStatus) == -1)
         return -1;
+#else
+    if (_stat (name.c_str (), &fileStatus) == -1)
+        return -1;
+#endif
     
     fi->mtime = helpers::Time (fileStatus.st_mtime);
     fi->is_link = false;
index e9fd1e3371ec291121f2e12e927f1e74ef3975ff..f027fb7c9f214950a78239a4f5a3386cecdf6922 100644 (file)
@@ -137,9 +137,9 @@ LogLevelMatchFilter::decide(const InternalLoggingEvent& event) const
         return NEUTRAL;
     }
 
-    bool matchOccured = (logLevelToMatch == event.getLogLevel());
+    bool matchOccurred = (logLevelToMatch == event.getLogLevel());
        
-    if(matchOccured) {
+    if(matchOccurred) {
         return (acceptOnMatch ? ACCEPT : DENY);
     }
     else {
index 8227e5322a5e6acb9387b0e7aeb01b9bf3db6f22..6da22c8001c23903078019434f43d497e7feee8b 100644 (file)
@@ -42,7 +42,7 @@ namespace dcmtk
 namespace log4cplus
 {
 
-#ifdef UNICODE
+#ifdef DCMTK_OFLOG_UNICODE
 DCMTK_LOG4CPLUS_EXPORT tostream & tcout = STD_NAMESPACE wcout;
 DCMTK_LOG4CPLUS_EXPORT tostream & tcerr = STD_NAMESPACE wcerr;
 
index 803fcb7298f945f3ca551b3bd01fcd1a6c619a23..c79831ea31a49c53d2094ecaed93803bc1956817 100644 (file)
@@ -29,7 +29,7 @@
 #include "dcmtk/oflog/thread/syncpub.h"
 #include <iomanip>
 #include <cstring>
-#if defined (UNICODE)
+#if defined (DCMTK_OFLOG_UNICODE)
 #include <cwctype>
 #else
 #include <cctype>
@@ -48,7 +48,7 @@ namespace
 static inline bool
 is_control (tchar ch)
 {
-#if defined (UNICODE)
+#if defined (DCMTK_OFLOG_UNICODE)
     return !! STD_NAMESPACE iswcntrl (STD_NAMESPACE char_traits<tchar>::to_int_type (ch));
 #elif defined (_MSC_VER) && _MSC_VER <= 1200 /* MSC6 and older */
     return !! iscntrl (STD_NAMESPACE char_traits<tchar>::to_int_type (ch));
@@ -175,7 +175,7 @@ Log4jUdpAppender::~Log4jUdpAppender()
 // Log4jUdpAppender public methods
 //////////////////////////////////////////////////////////////////////////////
 
-void 
+void
 Log4jUdpAppender::close()
 {
     helpers::getLogLog().debug(
index 6d009d5dd1d4541beede022da2debb95b0c1a571..e39475357c2d7d3d5d8dff59f3f56993b778bafa 100644 (file)
@@ -46,7 +46,7 @@ namespace {
 
     static
     bool
-    copySID(SID** ppDstSid, SID* pSrcSid) 
+    copySID(SID** ppDstSid, SID* pSrcSid)
     {
         DWORD dwLength = ::GetLengthSid(pSrcSid);
 
@@ -68,8 +68,8 @@ namespace {
 
 
     static
-    bool 
-    GetCurrentUserSID(SID** ppSid) 
+    bool
+    GetCurrentUserSID(SID** ppSid)
     {
         bool bSuccess = false;
         TOKEN_USER * ptu = 0;
@@ -102,44 +102,56 @@ namespace {
 
 
     static
-    HKEY 
+    HKEY
     regGetKey(const tstring& subkey, DWORD* disposition)
     {
         HKEY hkey = 0;
-        RegCreateKeyEx(HKEY_LOCAL_MACHINE, 
-                       subkey.c_str(), 
-                       0, 
-                       NULL, 
-                       REG_OPTION_NON_VOLATILE, 
-                       KEY_SET_VALUE, 
-                       NULL, 
-                       &hkey, 
+#if defined (DCMTK_OFLOG_UNICODE)
+        RegCreateKeyEx(HKEY_LOCAL_MACHINE,
+#else
+        RegCreateKeyExA(HKEY_LOCAL_MACHINE,
+#endif
+                       subkey.c_str(),
+                       0,
+                       NULL,
+                       REG_OPTION_NON_VOLATILE,
+                       KEY_SET_VALUE,
+                       NULL,
+                       &hkey,
                        disposition);
         return hkey;
     }
 
 
     static
-    void 
+    void
     regSetString(HKEY hkey, const tstring& name, const tstring& value)
     {
-        RegSetValueEx(hkey, 
-                      name.c_str(), 
-                      0, 
-                      REG_SZ, 
+#if defined (DCMTK_OFLOG_UNICODE)
+        RegSetValueEx(hkey,
+#else
+        RegSetValueExA(hkey,
+#endif
+                      name.c_str(),
+                      0,
+                      REG_SZ,
                       OFreinterpret_cast(BYTE const *, value.c_str()),
                       OFstatic_cast(DWORD, value.length() * sizeof(tchar)));
     }
 
 
     static
-    void 
+    void
     regSetDword(HKEY hkey, const tstring& name, DWORD value)
     {
-        RegSetValueEx(hkey, 
-                      name.c_str(), 
-                      0, 
-                      REG_DWORD, 
+#if defined (DCMTK_OFLOG_UNICODE)
+        RegSetValueEx(hkey,
+#else
+        RegSetValueExA(hkey,
+#endif
+                      name.c_str(),
+                      0,
+                      REG_DWORD,
                       OFreinterpret_cast(LPBYTE, &value),
                       OFstatic_cast(DWORD, sizeof(DWORD)));
     }
@@ -152,13 +164,13 @@ namespace {
 // NTEventLogAppender ctor and dtor
 //////////////////////////////////////////////////////////////////////////////
 
-NTEventLogAppender::NTEventLogAppender(const tstring& server, 
-                                       const tstring& log, 
+NTEventLogAppender::NTEventLogAppender(const tstring& server,
+                                       const tstring& log,
                                        const tstring& source)
-: server(server), 
-  log(log), 
-  source(source), 
-  hEventLog(NULL), 
+: server(server),
+  log(log),
+  source(source),
+  hEventLog(NULL),
   pCurrentUserSID(NULL)
 {
     init();
@@ -171,7 +183,7 @@ NTEventLogAppender::NTEventLogAppender(const helpers::Properties & properties)
   server(properties.getProperty( DCMTK_LOG4CPLUS_TEXT("server") )),
   log(properties.getProperty( DCMTK_LOG4CPLUS_TEXT("log") )),
   source(properties.getProperty( DCMTK_LOG4CPLUS_TEXT("source") )),
-  hEventLog(NULL), 
+  hEventLog(NULL),
   pCurrentUserSID(NULL)
 {
     init();
@@ -179,13 +191,13 @@ NTEventLogAppender::NTEventLogAppender(const helpers::Properties & properties)
 
 
 
-void 
+void
 NTEventLogAppender::init()
 {
     if(source.empty()) {
         helpers::getLogLog().warn(
             DCMTK_LOG4CPLUS_TEXT("Source option not set for appender [")
-            + name 
+            + name
             + DCMTK_LOG4CPLUS_TEXT("]."));
         return;
     }
@@ -199,8 +211,13 @@ NTEventLogAppender::init()
 
     addRegistryInfo();
 
+#if defined (DCMTK_OFLOG_UNICODE)
     hEventLog = ::RegisterEventSource(server.empty () ? 0 : server.c_str(),
         source.c_str());
+#else
+    hEventLog = ::RegisterEventSourceA(server.empty () ? 0 : server.c_str(),
+        source.c_str());
+#endif
     if (! hEventLog || hEventLog == HANDLE(ERROR_INVALID_HANDLE))
         helpers::getLogLog().warn (
             DCMTK_LOG4CPLUS_TEXT("Event source registration failed."));
@@ -224,7 +241,7 @@ NTEventLogAppender::~NTEventLogAppender()
 // NTEventLogAppender public methods
 //////////////////////////////////////////////////////////////////////////////
 
-void 
+void
 NTEventLogAppender::close()
 {
     if(hEventLog != NULL) {
@@ -240,7 +257,7 @@ NTEventLogAppender::close()
 // NTEventLogAppender protected methods
 //////////////////////////////////////////////////////////////////////////////
 
-void 
+void
 NTEventLogAppender::append(const spi::InternalLoggingEvent& event)
 {
     if(hEventLog == NULL) {
@@ -256,7 +273,11 @@ NTEventLogAppender::append(const spi::InternalLoggingEvent& event)
         str.resize (31839);
 
     const tchar * s = str.c_str ();
+#if defined (DCMTK_OFLOG_UNICODE)
     BOOL bSuccess = ::ReportEvent(hEventLog,
+#else
+    BOOL bSuccess = ::ReportEventA(hEventLog,
+#endif
                                   getEventType(event),
                                   getEventCategory(event),
                                   0x1000,
@@ -275,7 +296,7 @@ NTEventLogAppender::append(const spi::InternalLoggingEvent& event)
 
 
 
-WORD 
+WORD
 NTEventLogAppender::getEventType(const spi::InternalLoggingEvent& event)
 {
     WORD ret_val;
@@ -293,7 +314,7 @@ NTEventLogAppender::getEventType(const spi::InternalLoggingEvent& event)
 
 
 
-WORD 
+WORD
 NTEventLogAppender::getEventCategory(const spi::InternalLoggingEvent& event)
 {
     WORD ret_val;
@@ -317,28 +338,28 @@ NTEventLogAppender::getEventCategory(const spi::InternalLoggingEvent& event)
 
 
 // Add this source with appropriate configuration keys to the registry.
-void 
+void
 NTEventLogAppender::addRegistryInfo()
 {
     DWORD disposition;
     HKEY hkey = 0;
     tstring subkey =   DCMTK_LOG4CPLUS_TEXT("SYSTEM\\CurrentControlSet\\Services\\EventLog\\")
-                     + log 
-                     + DCMTK_LOG4CPLUS_TEXT("\\") 
+                     + log
+                     + DCMTK_LOG4CPLUS_TEXT("\\")
                      + source;
-    
+
     hkey = regGetKey(subkey, &disposition);
     if(disposition == REG_CREATED_NEW_KEY) {
-        regSetString(hkey, 
-                     DCMTK_LOG4CPLUS_TEXT("EventMessageFile"), 
+        regSetString(hkey,
+                     DCMTK_LOG4CPLUS_TEXT("EventMessageFile"),
                      DCMTK_LOG4CPLUS_TEXT("NTEventLogAppender.dll"));
-        regSetString(hkey, 
-                     DCMTK_LOG4CPLUS_TEXT("CategoryMessageFile"), 
+        regSetString(hkey,
+                     DCMTK_LOG4CPLUS_TEXT("CategoryMessageFile"),
                      DCMTK_LOG4CPLUS_TEXT("NTEventLogAppender.dll"));
         regSetDword(hkey, DCMTK_LOG4CPLUS_TEXT("TypesSupported"), OFstatic_cast(DWORD, 7));
         regSetDword(hkey, DCMTK_LOG4CPLUS_TEXT("CategoryCount"), OFstatic_cast(DWORD, 5));
     }
-    
+
     RegCloseKey(hkey);
     return;
 }
index 85b55d880921660330e49b763575151e2a3d1ac6..ba47a7d8bc692e4d3736f09bac21a20a3f9c7ca0 100644 (file)
@@ -21,7 +21,7 @@
 #include "dcmtk/oflog/config.h"
 
 #include <cstring>
-#if defined (UNICODE)
+#if defined (DCMTK_OFLOG_UNICODE)
 #  include <cwctype>
 #else
 #  include <cctype>
@@ -58,7 +58,7 @@ static
 int
 is_space (tchar ch)
 {
-#if defined (UNICODE)
+#if defined (DCMTK_OFLOG_UNICODE)
     return STD_NAMESPACE iswspace (ch);
 #else
     return isspace (OFstatic_cast(unsigned char, ch));
@@ -133,7 +133,7 @@ Properties::Properties(const tstring& inputFile, unsigned flags) : data()
 
     switch (flags & fEncodingMask)
     {
-#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF8_FACET) && defined (UNICODE)
+#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF8_FACET) && defined (DCMTK_OFLOG_UNICODE)
     case fUTF8:
         file.imbue (
             STD_NAMESPACE locale (file.getloc (),
@@ -142,7 +142,7 @@ Properties::Properties(const tstring& inputFile, unsigned flags) : data()
         break;
 #endif
 
-#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF16_FACET) && defined (UNICODE)
+#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF16_FACET) && defined (DCMTK_OFLOG_UNICODE)
     case fUTF16:
         file.imbue (
             STD_NAMESPACE locale (file.getloc (),
@@ -150,7 +150,7 @@ Properties::Properties(const tstring& inputFile, unsigned flags) : data()
                     OFstatic_cast(STD_NAMESPACE codecvt_mode, STD_NAMESPACE consume_header | STD_NAMESPACE little_endian)>));
         break;
 
-#elif defined (UNICODE) && defined (WIN32)
+#elif defined (DCMTK_OFLOG_UNICODE) && defined (WIN32)
     case fUTF16:
         file.imbue (
             STD_NAMESPACE locale (file.getloc (),
@@ -159,7 +159,7 @@ Properties::Properties(const tstring& inputFile, unsigned flags) : data()
 
 #endif
 
-#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF32_FACET) && defined (UNICODE)
+#if defined (DCMTK_LOG4CPLUS_HAVE_CODECVT_UTF32_FACET) && defined (DCMTK_OFLOG_UNICODE)
     case fUTF32:
         file.imbue (
             STD_NAMESPACE locale (file.getloc (),
index bbf59cb205ca2fa765c9eb86eafe2b67fffed9e5..7602942a1c59352a18018c297b45aacd372d60ce 100644 (file)
@@ -26,7 +26,7 @@
 #include "dcmtk/oflog/internal/internal.h"
 #include <cstdarg>
 #include <cstdio>
-#if defined (UNICODE)
+#if defined (DCMTK_OFLOG_UNICODE)
 #include <cwchar>
 #endif
 #if defined (DCMTK_LOG4CPLUS_HAVE_STDARG_H)
@@ -66,7 +66,7 @@ static inline
 int
 vftprintf (STD_NAMESPACE FILE * file, tchar const * fmt, va_list args)
 {
-#if defined (UNICODE)
+#if defined (DCMTK_OFLOG_UNICODE)
 #  if defined (DCMTK_LOG4CPLUS_HAVE_VFWPRINTF_S)
     return vfwprintf_s (file, fmt, args);
 #  else
@@ -92,7 +92,7 @@ vstprintf (tchar * dest, size_t dest_size, tchar const * fmt,
     va_list args)
 {
     int ret;
-#if defined (UNICODE)
+#if defined (DCMTK_OFLOG_UNICODE)
 #  if defined (DCMTK_LOG4CPLUS_HAVE_VSWPRINTF_S)
     ret = vswprintf_s (dest, dest_size, fmt, args);
 #  else
@@ -125,7 +125,7 @@ vsntprintf (tchar * dest, size_t dest_size, tchar const * fmt,
 {
     int ret;
 
-#if defined (UNICODE)
+#if defined (DCMTK_OFLOG_UNICODE)
 #  if defined (DCMTK_LOG4CPLUS_HAVE__VSNWPRINTF_S) && defined (_TRUNCATE)
     ret = _vsnwprintf_s (dest, dest_size, _TRUNCATE, fmt, args);
 #  else
index 52bb25060559187c2f9471d70bad5d4a67df6b9c..f17bf4fdc0dba2a438254509bac5ba4a0351d38c 100644 (file)
@@ -150,7 +150,7 @@ SocketBuffer::readString(unsigned char sizeOfChar)
         strlen = bufferLen / sizeOfChar;
     }
 
-#ifndef UNICODE
+#ifndef DCMTK_OFLOG_UNICODE
     if(sizeOfChar == 1) {
         tstring ret(&buffer[pos], strlen);
         pos += strlen;
@@ -168,7 +168,7 @@ SocketBuffer::readString(unsigned char sizeOfChar)
         getLogLog().error(DCMTK_LOG4CPLUS_TEXT("SocketBuffer::readString()- Invalid sizeOfChar!!!!"));
     }
 
-#else /* UNICODE */
+#else /* DCMTK_OFLOG_UNICODE */
     if(sizeOfChar == 1) {
         STD_NAMESPACE string ret(&buffer[pos], strlen);
         pos += strlen;
@@ -252,7 +252,7 @@ SocketBuffer::appendString(const tstring& str)
     }
 
     appendInt(OFstatic_cast(unsigned, strlen));
-#ifndef UNICODE
+#ifndef DCMTK_OFLOG_UNICODE
     memcpy(&buffer[pos], str.data(), strlen);
     pos += strlen;
     size = pos;
index 6b9596aa90a05c0adfa5f1c62e356b55fd28ad68..4e81da7ec8073764cbbb1865a0bf782834daa045 100644 (file)
@@ -276,7 +276,7 @@ convertToBuffer(SocketBuffer & buffer,
     const tstring& serverName)
 {
     buffer.appendByte(DCMTK_LOG4CPLUS_MESSAGE_VERSION);
-#ifndef UNICODE
+#ifndef DCMTK_OFLOG_UNICODE
     buffer.appendByte(1);
 #else
     buffer.appendByte(2);
index ef1a3a511fd9824c29d727845fdc1e1337b7f2a7..859555b0796092edd6fb04cff61e0d280f0ebe9f 100644 (file)
@@ -52,7 +52,7 @@ tstring const empty_str;
 // Global Methods
 //////////////////////////////////////////////////////////////////////////////
 
-#if defined (UNICODE) && defined (DCMTK_LOG4CPLUS_ENABLE_GLOBAL_C_STRING_STREAM_INSERTER)
+#if defined (DCMTK_OFLOG_UNICODE) && defined (DCMTK_LOG4CPLUS_ENABLE_GLOBAL_C_STRING_STREAM_INSERTER)
 
 log4cplus::tostream& 
 operator <<(log4cplus::tostream& stream, const char* str)
@@ -171,7 +171,7 @@ struct toupper_func
     operator () (tchar ch) const
     {
         return STD_NAMESPACE char_traits<tchar>::to_char_type (
-#ifdef UNICODE
+#ifdef DCMTK_OFLOG_UNICODE
             STD_NAMESPACE towupper
 #else
             toupper
@@ -187,7 +187,7 @@ struct tolower_func
     operator () (tchar ch) const
     {
         return STD_NAMESPACE char_traits<tchar>::to_char_type (
-#ifdef UNICODE
+#ifdef DCMTK_OFLOG_UNICODE
             STD_NAMESPACE towlower
 #else
             tolower
index c36c0848188d918e20db7ee8193d6334ee5e247c..993f298e82eee168ba0ebe3260d3a4b249829034 100644 (file)
@@ -29,7 +29,7 @@
 #include <iomanip>
 #include <cassert>
 #include <cerrno>
-#if defined (UNICODE)
+#if defined (DCMTK_OFLOG_UNICODE)
 #include <cwchar>
 #endif
 
@@ -69,7 +69,7 @@ const int ONE_SEC_IN_USEC = 1000000;
 using STD_NAMESPACE mktime;
 using STD_NAMESPACE gmtime;
 using STD_NAMESPACE localtime;
-#if defined (UNICODE)
+#if defined (DCMTK_OFLOG_UNICODE)
 using STD_NAMESPACE wcsftime;
 #else
 using STD_NAMESPACE strftime;
@@ -281,7 +281,7 @@ Time::getFormattedTime(const log4cplus::tstring& fmt_orig, bool use_gmtime) cons
     gft_sp.ret.reserve (OFstatic_cast(size_t, OFstatic_cast(double, gft_sp.fmt.size ()) * 1.35));
     State state = TEXT;
 
-    // Walk the format string and process all occurences of %q and %Q.
+    // Walk the format string and process all occurrences of %q and %Q.
 
     for (log4cplus::tstring::const_iterator fmt_it = gft_sp.fmt.begin ();
          fmt_it != gft_sp.fmt.end (); ++fmt_it)
@@ -368,7 +368,7 @@ Time::getFormattedTime(const log4cplus::tstring& fmt_orig, bool use_gmtime) cons
     {
         gft_sp.buffer.resize (buffer_size);
         errno = 0;
-#ifdef UNICODE
+#ifdef DCMTK_OFLOG_UNICODE
         len = wcsftime(&gft_sp.buffer[0], buffer_size,
             gft_sp.fmt.c_str(), &time);
 #else
index e6269a87a50a20f0cca97c068f71398f383c3bf5..45d2b44e3e7aaac60324460b8c8ab719e8543a24 100644 (file)
@@ -119,7 +119,7 @@ Win32ConsoleAppender::write_handle (void * outvoid, tchar const * s,
     size_t str_len)
 {
     HANDLE out = OFstatic_cast(HANDLE, outvoid);
-#if defined (UNICODE)
+#if defined (DCMTK_OFLOG_UNICODE)
     STD_NAMESPACE wstring wstr (s, str_len);
     STD_NAMESPACE string str (helpers::tostring (wstr));
     str_len = str.size ();
index acf564bcf703d1a6d6b082567f9fbfaee455fe6d..47108a434c763afed8ee9b4dd99c95e442aaf2aa 100644 (file)
@@ -79,7 +79,11 @@ void
 Win32DebugAppender::append(const spi::InternalLoggingEvent& event)
 {
     const tchar * s = formatEvent (event).c_str();
+#if defined (DCMTK_OFLOG_UNICODE)
     ::OutputDebugString(s);
+#else
+    ::OutputDebugStringA(s);
+#endif
 }
 
 
index f67fdb344b800df319d43afeef617fceeb80e119..bf13596b0e44568ef63c6f9bb49402adec5e375d 100644 (file)
@@ -235,9 +235,15 @@ connectSocket(const tstring& hostn, unsigned short port, bool udp, SocketState&
     {
         insock.sin_family = AF_INET;
         INT insock_size = OFstatic_cast(int, sizeof (insock));
+#if defined (DCMTK_OFLOG_UNICODE)
         INT ret = WSAStringToAddress (OFconst_cast(LPTSTR, hostn.c_str ()),
             AF_INET, 0, OFreinterpret_cast(struct sockaddr *, &insock),
             &insock_size);
+#else
+        INT ret = WSAStringToAddressA (OFconst_cast(LPSTR, hostn.c_str ()),
+            AF_INET, 0, OFreinterpret_cast(struct sockaddr *, &insock),
+            &insock_size);
+#endif
         if (ret == SOCKET_ERROR || insock_size != sizeof (insock)) 
         {
             state = bad_address;
index 4a974b4a958d922b7b8dcc63c5af7955f3a27523..b00b5de95b3c4a8cb5d074246b600590f67a984b 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2002-2017, OFFIS e.V.
+ *  Copyright (C) 2002-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
  *  class declaration  *
  *---------------------*/
 
-/** This class is a combination of OFDate and OFTime
+/** This class is a combination of OFDate and OFTime.
+ *  @note Please note that support for the leap second is limited: a value of
+ *    60 seconds is accepted (i.e. regarded as valid) but calculations based on
+ *    such a time value might be incorrect.
  */
 class DCMTK_OFSTD_EXPORT OFDateTime
 {
index a315a256be4d9cd806a2ce7b12aee99116c35a30..6f220d302821e57a894edc0078de0b92d163fc38 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2018, OFFIS e.V.
+ *  Copyright (C) 2018-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -36,6 +36,8 @@
 #define EXITCODE_COMMANDLINE_SYNTAX_ERROR         1
 #define EXITCODE_INSUFFICIENT_PRIVILEGES          2
 #define EXITCODE_SETUID_FAILED                    3
+#define EXITCODE_MEMORY_EXHAUSTED                 4
+#define EXITCODE_NOOPENSSL                        5
 
 // input file errors (20-39)
 #define EXITCODE_CANNOT_READ_INPUT_FILE          20
@@ -54,7 +56,7 @@
 // processing errors (80-99)
 // - defined in the respective modules / tools
 
-// user-defined errors (100-119)
+// application-specific or user-defined errors (100-127)
 // - defined in the respective modules / tools
 
 // GNU recommends that the codes 128-255 be reserved for serious errors:
index 7ef3fc9e00073ee3252d1d88e69641f105a61cbf..6446e0af7ceb455da57d7028685d2da3d31d0983 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2006-2019, OFFIS e.V.
+ *  Copyright (C) 2006-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -131,7 +131,7 @@ public:
   /** constructor expecting a conventional character string
    *  @param filename filename to be stored (8-bit characters, e.g. UTF-8)
    *  @param convert  convert given filename to wide character encoding as an
-   *    alternative representation
+   *    alternative representation.  Only works on Windows systems.
    */
   OFFilename(const char *filename,
              const OFBool convert = OFFalse);
@@ -144,18 +144,20 @@ public:
   OFFilename(const OFString &filename,
              const OFBool convert = OFFalse);
 
-  /** construct an OFFilename from an OFpath.
-   *  @param path the OFpath object referring to a file.
-   *  Effectively OFFilename(path.native(), OFTrue), but potentially more
-   *  efficient.
+  /** constructor expecting an OFpath instance
+   *  @param path    OFpath instance storing a filename in native format
+   *    (currently, identical to an 8-bit character string)
+   *  @param convert convert given filename to wide character encoding as an
+   *    alternative representation.  Only works on Windows systems.
    */
-  OFFilename(const OFpath& path);
+  OFFilename(const OFpath &path,
+             const OFBool convert = OFFalse);
 
 #if (defined(WIDE_CHAR_FILE_IO_FUNCTIONS) || defined(WIDE_CHAR_MAIN_FUNCTION)) && defined(_WIN32)
   /** constructor expecting a wide character string
    *  @remark This constructor is only available if DCMTK is compiled on Windows
-   *  Operating Systems with wide chars enabled (defining _WIN32 as well as
-   *  WIDE_CHAR_FILE_IO_FUNCTIONS or WIDE_CHAR_MAIN_FUNCTION).
+   *    Operating Systems with wide chars enabled (defining _WIN32 as well as
+   *    WIDE_CHAR_FILE_IO_FUNCTIONS or WIDE_CHAR_MAIN_FUNCTION).
    *  @param filename filename to be stored (e.g. 16-bit characters)
    *  @param convert  convert given filename to UTF-8 encoding as an
    *    alternative representation.  Only works on Windows systems.
@@ -217,8 +219,8 @@ public:
 #if (defined(WIDE_CHAR_FILE_IO_FUNCTIONS) || defined(WIDE_CHAR_MAIN_FUNCTION)) && defined(_WIN32)
   /** get stored filename consisting of wide characters
    *  @remark This method is only available if DCMTK is compiled on Windows
-   *  Operating Systems with wide chars enabled (defining _WIN32 as well as
-   *  WIDE_CHAR_FILE_IO_FUNCTIONS or WIDE_CHAR_MAIN_FUNCTION).
+   *    Operating Systems with wide chars enabled (defining _WIN32 as well as
+   *    WIDE_CHAR_FILE_IO_FUNCTIONS or WIDE_CHAR_MAIN_FUNCTION).
    *  @return wide char filename (might be NULL if none is stored)
    */
   inline const wchar_t *getWideCharPointer() const
@@ -243,11 +245,20 @@ public:
   void set(const OFString &filename,
            const OFBool convert = OFFalse);
 
+  /** replace currently stored filename by given value
+   *  @param OFpath  OFpath instance storing a filename in native format
+   *    (currently, identical to an 8-bit character string)
+   *  @param convert convert given filename to wide character encoding as an
+   *    alternative representation).  Only works on Windows systems.
+   */
+  void set(const OFpath &path,
+           const OFBool convert = OFFalse);
+
 #if (defined(WIDE_CHAR_FILE_IO_FUNCTIONS) || defined(WIDE_CHAR_MAIN_FUNCTION)) && defined(_WIN32)
   /** replace currently stored filename by given value
    *  @remark This method is only available if DCMTK is compiled on Windows
-   *  Operating Systems with wide chars enabled (defining _WIN32 as well as
-   *  WIDE_CHAR_FILE_IO_FUNCTIONS or WIDE_CHAR_MAIN_FUNCTION).
+   *    Operating Systems with wide chars enabled (defining _WIN32 as well as
+   *    WIDE_CHAR_FILE_IO_FUNCTIONS or WIDE_CHAR_MAIN_FUNCTION).
    *  @param filename filename to be stored (e.g. 16-bit characters)
    *  @param convert  convert given filename to UTF-8 encoding as an alternative
    *    representation.  Only works on Windows systems.
@@ -258,12 +269,12 @@ public:
 
 private:
   /// filename consisting of conventional characters (8-bit, e.g.\ UTF-8)
-  /// @remark This member is only available if DCMTK is compiled on Windows
-  /// Operating Systems with wide chars enabled (defining _WIN32 as well as
-  /// WIDE_CHAR_FILE_IO_FUNCTIONS or WIDE_CHAR_MAIN_FUNCTION).
   char *filename_;
 #if (defined(WIDE_CHAR_FILE_IO_FUNCTIONS) || defined(WIDE_CHAR_MAIN_FUNCTION)) && defined(_WIN32)
   /// filename consisting of wide characters (e.g. 16-bit on Windows)
+  /// @remark This member is only available if DCMTK is compiled on Windows
+  ///   Operating Systems with wide chars enabled (defining _WIN32 as well as
+  ///   WIDE_CHAR_FILE_IO_FUNCTIONS or WIDE_CHAR_MAIN_FUNCTION).
   wchar_t *wfilename_;
 #endif
 };
@@ -341,8 +352,8 @@ public:
   /** opens the file whose name is the wide character string pointed to by path and
    *  associates a stream with it.
    *  @remark This member is only available if DCMTK is compiled on Windows
-   *  Operating Systems with wide chars enabled (defining _WIN32 as well as
-   *  WIDE_CHAR_FILE_IO_FUNCTIONS).
+   *    Operating Systems with wide chars enabled (defining _WIN32 as well as
+   *    WIDE_CHAR_FILE_IO_FUNCTIONS).
    *  @param filename Unicode filename path to file
    *  @param modes "r", "w" or "a" with possible modifiers "+", "b", as a wide
    *    character string
index 50e5e125689533b983869e58d27a8c92e1104088..13f731b5e79de6880caaf3712c2f8f9520a099db 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2014-2017, OFFIS e.V.
+ *  Copyright (C) 2014-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -983,7 +983,6 @@ struct OFnumeric_limits
     static inline T denorm_min()                    { return T(); }
 };
 
-#ifdef HAVE_CXX_BOOL
 template<>
 struct OFnumeric_limits<bool>
 {
@@ -1020,7 +1019,6 @@ struct OFnumeric_limits<bool>
     static inline bool signaling_NaN()              { return OFFalse; }
     static inline bool denorm_min()                 { return OFFalse; }
 };
-#endif
 
 template<>
 struct OFnumeric_limits<char>
index bcc07ba1032ad251cebf57500a7acbea4114d354..7a4252779c72b07fc2322910189be7797c5d6cab 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2009-2017, OFFIS e.V.
+ *  Copyright (C) 2009-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -209,11 +209,25 @@ public:
      */
     OFPair<iterator, bool> insert(const value_type& val)
     {
+        // If value already exists, return it
         OFListIterator(value_type) it = find(val.first);
         if (it != end())
             return OFMake_pair(it, false);
 
-        it = values_.insert(values_.end(), val);
+        // Sorted insertion
+        it = begin();
+        while ( (it != end()) && (val.first > it->first) )
+            it++;
+        if (it == end())
+            it = values_.insert(values_.end(), val);
+        else
+        {
+            // Insert at current position and rewind iterator
+            // to the inserted element
+            values_.insert(it, val);
+            it--;
+        }
+
         return OFMake_pair(it, true);
     }
 
index 0eb070b7331a27bf43d3fa5c2d7aa12c41ae57f1..18b0b5f375f0379f62768ffa4dcd0d0dfea9f72c 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2011-2012, OFFIS e.V.
+ *  Copyright (C) 2011-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This code is inspired by quicktest.
@@ -207,7 +207,7 @@ public:
             return 254;
         }
 
-        return numFailed;
+        return OFstatic_cast(int, numFailed);
     }
 
     /** Handle the given arguments and run the requested test case. This
index cfeb3d4c7c94460b82b5a0e6fe1b5d2a8a2859c1..bcc62133b3007deeff747e8723c08de1b6fe724e 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2002-2011, OFFIS e.V.
+ *  Copyright (C) 2002-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -41,7 +41,10 @@ END_EXTERN_C
  *  class declaration  *
  *---------------------*/
 
-/** This class provides a collection of time functions
+/** This class provides a collection of time functions.
+ *  @note Please note that support for the leap second is limited: a value of
+ *    60 seconds is accepted (i.e. regarded as valid) but calculations based on
+ *    such a time value might be incorrect.
  */
 class DCMTK_OFSTD_EXPORT OFTime
 {
@@ -138,8 +141,8 @@ class DCMTK_OFSTD_EXPORT OFTime
     virtual void clear();
 
     /** check whether the currently stored time value is valid.
-     *  Valid ranges: [0,24[ for 'hour', [0,60[ for 'minute', [0.0,60.0[ for 'second'
-     *  and [-12.0,+14.0] for 'timeZone'
+     *  Valid ranges: [0,24[ for 'hour', [0,60[ for 'minute', [0.0,60.0] for 'second'
+     *  (including leap second) and [-12.0,+14.0] for 'timeZone'
      *  @return OFTrue if the current value is valid, OFFalse otherwise
      */
     virtual OFBool isValid() const;
index 3e8f7755364d1f1549f2440ebef35dd55d19b2b1..65081d8ca3987424cfde591bb0e6e4c5ccd99c87 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2014-2017, OFFIS e.V.
+ *  Copyright (C) 2014-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -138,10 +138,8 @@ struct OFremove_volatile { typedef T type; };
 template<typename T>
 struct OFremove_extent { typedef T type; };
 
-#ifdef HAVE_CXX_BOOL
 template<>
 struct OFis_unsigned<bool> : OFtrue_type {};
-#endif
 
 #ifndef C_CHAR_UNSIGNED
 template<>
index 63eef5adbca8353a51da6862961fb45033267be9..436daa032d10b2044b4000650e641d7ffbf2575d 100644 (file)
@@ -163,30 +163,10 @@ typedef Uint64 OFuintptr_t;
 
 // Definition of type OFBool
 
-#ifdef HAVE_CXX_BOOL
-
-#define OFBool bool
+typedef bool OFBool;
 #define OFTrue true
 #define OFFalse false
 
-#else
-
-/** the boolean type used throughout the DCMTK project. Mapped to the
- *  built-in type "bool" if the current C++ compiler supports it. Mapped
- *  to int for old-fashioned compilers which do not yet support bool.
- */
-typedef int OFBool;
-
-#ifndef OFTrue
-#define OFTrue (1)
-#endif
-
-#ifndef OFFalse
-#define OFFalse (0)
-#endif
-
-#endif
-
 #if defined(HAVE_TYPENAME)
 #define OFTypename typename
 #else
index f74dac8ff1118aab90380c5669af4f560bf22ff8..06d2e85a4656b247b96602f411d58447cef67552 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2011-2019, OFFIS e.V.
+ *  Copyright (C) 2011-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were slightly modified by
@@ -78,9 +78,8 @@
  * full-fledged HTML documentation using the DOXYGEN software: simply type: "doxygen doxy.cfg"
  *
  * By default, the XMLParser library uses (char*) for string representation.To use the (wchar_t*)
- * version of the library, you need to define the "_UNICODE" preprocessor definition variable
- * (this is usually done inside your project definition file) (This is done automatically for you
- * when using Visual Studio).
+ * version of the library, you need to define the "WIDE_CHAR_XML_PARSER" preprocessor definition variable
+ * (this is usually done inside your project definition file)
  *
  * \section example Advanced Tutorial and Many Examples of usage.
  *
 #include "dcmtk/ofstd/ofstdinc.h"
 #include "dcmtk/ofstd/ofdefine.h"
 
-// DCMTK: we might want to enable wide characters without the "official" defines
-#if defined(UNICODE) || defined(_UNICODE) || defined(WIDE_CHAR_XML_PARSER)
-// If you comment the next "define" line then the library will never "switch to" _UNICODE (wchar_t*) mode (16/32 bits per characters).
-// This is useful when you get error messages like:
-//    'XMLNode::openFileHelper' : cannot convert parameter 2 from 'const char [5]' to 'const wchar_t *'
-// The _XMLWIDECHAR preprocessor variable force the XMLParser library into either utf16/32-mode (the preprocessor variable
-// must be defined) or utf8-mode (the pre-processor variable must be undefined).
+// DCMTK: The XML parser is compiled in wide char (UTF-16) mode if and only if this macro is defined.
+// We want this to be independent from the UNICODE/_UNICODE macros.
+#ifdef WIDE_CHAR_XML_PARSER
 #define _XMLWIDECHAR
 #endif
 
index c90c78701c03e3c3b9f4939dd539d403cb41ba52..ad85ec11c3f9b1cd21735e00a9f48eda1ca7c926 100644 (file)
@@ -6,14 +6,10 @@ ofchrenc.o: ofchrenc.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofstring.h ../include/dcmtk/ofstd/ofmem.h \
  ../include/dcmtk/ofstd/ofutil.h ../include/dcmtk/ofstd/oftraits.h \
  ../include/dcmtk/ofstd/variadic/tuplefwd.h \
- ../include/dcmtk/ofstd/ofstd.h ../include/dcmtk/ofstd/oflist.h \
- ../include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
+ ../include/dcmtk/ofstd/ofthread.h ../include/dcmtk/ofstd/ofstd.h \
+ ../include/dcmtk/ofstd/oflist.h ../include/dcmtk/ofstd/oflimits.h \
  ../include/dcmtk/ofstd/oferror.h ../include/dcmtk/ofstd/ofdiag.h \
- ../include/dcmtk/ofstd/ofconsol.h ../include/dcmtk/ofstd/ofthread.h \
- ../include/dcmtk/ofstd/diag/push.def \
- ../include/dcmtk/ofstd/diag/shadow.def \
- ../include/dcmtk/ofstd/diag/pop.def
+ ../include/dcmtk/ofstd/ofconsol.h
 ofcmdln.o: ofcmdln.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofcmdln.h ../include/dcmtk/ofstd/oftypes.h \
  ../include/dcmtk/ofstd/ofdefine.h ../include/dcmtk/ofstd/ofcast.h \
@@ -23,10 +19,9 @@ ofcmdln.o: ofcmdln.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofstring.h ../include/dcmtk/ofstd/ofconsol.h \
  ../include/dcmtk/ofstd/ofthread.h ../include/dcmtk/ofstd/offile.h \
  ../include/dcmtk/ofstd/ofstd.h ../include/dcmtk/ofstd/ofcond.h \
- ../include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../include/dcmtk/ofstd/oferror.h ../include/dcmtk/ofstd/ofchrenc.h \
- ../include/dcmtk/ofstd/ofmem.h ../include/dcmtk/ofstd/ofutil.h \
+ ../include/dcmtk/ofstd/oflimits.h ../include/dcmtk/ofstd/oferror.h \
+ ../include/dcmtk/ofstd/ofchrenc.h ../include/dcmtk/ofstd/ofmem.h \
+ ../include/dcmtk/ofstd/ofutil.h \
  ../include/dcmtk/ofstd/variadic/tuplefwd.h
 ofconapp.o: ofconapp.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofconapp.h ../include/dcmtk/ofstd/oftypes.h \
@@ -38,11 +33,7 @@ ofconapp.o: ofconapp.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofconsol.h ../include/dcmtk/ofstd/ofthread.h \
  ../include/dcmtk/ofstd/offile.h ../include/dcmtk/ofstd/ofstd.h \
  ../include/dcmtk/ofstd/ofcond.h ../include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../include/dcmtk/ofstd/oferror.h ../include/dcmtk/ofstd/ofexit.h \
- ../include/dcmtk/ofstd/ofchrenc.h ../include/dcmtk/ofstd/ofmem.h \
- ../include/dcmtk/ofstd/ofutil.h \
- ../include/dcmtk/ofstd/variadic/tuplefwd.h
+ ../include/dcmtk/ofstd/oferror.h ../include/dcmtk/ofstd/ofexit.h
 ofcond.o: ofcond.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofcond.h ../include/dcmtk/ofstd/oftypes.h \
  ../include/dcmtk/ofstd/ofdefine.h ../include/dcmtk/ofstd/ofcast.h \
@@ -82,7 +73,6 @@ oferror.o: oferror.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofexport.h ../include/dcmtk/ofstd/ofstream.h \
  ../include/dcmtk/ofstd/ofstring.h ../include/dcmtk/ofstd/oftraits.h \
  ../include/dcmtk/ofstd/ofcond.h ../include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
  ../include/dcmtk/ofstd/oferror.h ../include/dcmtk/ofstd/ofdiag.h \
  ../include/dcmtk/ofstd/diag/push.def \
  ../include/dcmtk/ofstd/diag/vsprfw.def \
@@ -94,11 +84,11 @@ offile.o: offile.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofstream.h ../include/dcmtk/ofstd/ofstring.h \
  ../include/dcmtk/ofstd/ofstd.h ../include/dcmtk/ofstd/oflist.h \
  ../include/dcmtk/ofstd/oftraits.h ../include/dcmtk/ofstd/ofcond.h \
- ../include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../include/dcmtk/ofstd/oferror.h ../include/dcmtk/ofstd/offilsys.h \
- ../include/dcmtk/ofstd/ofmem.h ../include/dcmtk/ofstd/ofutil.h \
- ../include/dcmtk/ofstd/variadic/tuplefwd.h
+ ../include/dcmtk/ofstd/oflimits.h ../include/dcmtk/ofstd/oferror.h \
+ ../include/dcmtk/ofstd/offilsys.h ../include/dcmtk/ofstd/ofmem.h \
+ ../include/dcmtk/ofstd/ofutil.h \
+ ../include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../include/dcmtk/ofstd/ofthread.h
 offilsys.o: offilsys.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofstdinc.h ../include/dcmtk/ofstd/offilsys.h \
  ../include/dcmtk/ofstd/ofstring.h ../include/dcmtk/ofstd/oftypes.h \
@@ -106,7 +96,8 @@ offilsys.o: offilsys.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofexport.h ../include/dcmtk/ofstd/ofstream.h \
  ../include/dcmtk/ofstd/ofmem.h ../include/dcmtk/ofstd/ofutil.h \
  ../include/dcmtk/ofstd/oftraits.h \
- ../include/dcmtk/ofstd/variadic/tuplefwd.h
+ ../include/dcmtk/ofstd/variadic/tuplefwd.h \
+ ../include/dcmtk/ofstd/ofthread.h
 offname.o: offname.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/offname.h ../include/dcmtk/ofstd/oftypes.h \
  ../include/dcmtk/ofstd/ofdefine.h ../include/dcmtk/ofstd/ofcast.h \
@@ -114,9 +105,7 @@ offname.o: offname.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofstream.h ../include/dcmtk/ofstd/ofstring.h \
  ../include/dcmtk/ofstd/ofstd.h ../include/dcmtk/ofstd/oflist.h \
  ../include/dcmtk/ofstd/oftraits.h ../include/dcmtk/ofstd/ofcond.h \
- ../include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../include/dcmtk/ofstd/oferror.h
+ ../include/dcmtk/ofstd/oflimits.h ../include/dcmtk/ofstd/oferror.h
 oflist.o: oflist.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/oflist.h ../include/dcmtk/ofstd/oftypes.h \
  ../include/dcmtk/ofstd/ofdefine.h ../include/dcmtk/ofstd/ofcast.h \
@@ -135,9 +124,7 @@ ofrand.o: ofrand.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofstream.h ../include/dcmtk/ofstd/ofstd.h \
  ../include/dcmtk/ofstd/oflist.h ../include/dcmtk/ofstd/ofstring.h \
  ../include/dcmtk/ofstd/oftraits.h ../include/dcmtk/ofstd/ofcond.h \
- ../include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../include/dcmtk/ofstd/oferror.h
+ ../include/dcmtk/ofstd/oflimits.h ../include/dcmtk/ofstd/oferror.h
 ofsockad.o: ofsockad.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofsockad.h ../include/dcmtk/ofstd/ofdefine.h \
  ../include/dcmtk/ofstd/ofcast.h ../include/dcmtk/ofstd/ofexport.h \
@@ -149,7 +136,6 @@ ofstd.o: ofstd.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofstdinc.h ../include/dcmtk/ofstd/ofstream.h \
  ../include/dcmtk/ofstd/ofstring.h ../include/dcmtk/ofstd/oftraits.h \
  ../include/dcmtk/ofstd/ofcond.h ../include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
  ../include/dcmtk/ofstd/oferror.h ../include/dcmtk/ofstd/offile.h \
  ../include/dcmtk/ofstd/oftuple.h ../include/dcmtk/ofstd/ofutil.h \
  ../include/dcmtk/ofstd/variadic/tuplefwd.h \
@@ -168,9 +154,7 @@ ofstring.o: ofstring.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofstream.h ../include/dcmtk/ofstd/ofbmanip.h \
  ../include/dcmtk/ofstd/ofstd.h ../include/dcmtk/ofstd/oflist.h \
  ../include/dcmtk/ofstd/oftraits.h ../include/dcmtk/ofstd/ofcond.h \
- ../include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../include/dcmtk/ofstd/oferror.h
+ ../include/dcmtk/ofstd/oflimits.h ../include/dcmtk/ofstd/oferror.h
 ofstrutl.o: ofstrutl.cc ../include/dcmtk/ofstd/ofstrutl.h \
  ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofstring.h ../include/dcmtk/ofstd/oftypes.h \
@@ -185,17 +169,12 @@ oftempf.o: oftempf.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofstring.h ../include/dcmtk/ofstd/offname.h \
  ../include/dcmtk/ofstd/ofstd.h ../include/dcmtk/ofstd/oflist.h \
  ../include/dcmtk/ofstd/oftraits.h ../include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
  ../include/dcmtk/ofstd/oferror.h
 ofthread.o: ofthread.cc ../../config/include/dcmtk/config/osconfig.h \
- ../include/dcmtk/ofstd/ofstdinc.h ../include/dcmtk/ofstd/ofstd.h \
- ../include/dcmtk/ofstd/oflist.h ../include/dcmtk/ofstd/oftypes.h \
+ ../include/dcmtk/ofstd/ofthread.h ../include/dcmtk/ofstd/oftypes.h \
  ../include/dcmtk/ofstd/ofdefine.h ../include/dcmtk/ofstd/ofcast.h \
- ../include/dcmtk/ofstd/ofexport.h ../include/dcmtk/ofstd/ofstream.h \
- ../include/dcmtk/ofstd/ofstring.h ../include/dcmtk/ofstd/oftraits.h \
- ../include/dcmtk/ofstd/ofcond.h ../include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../include/dcmtk/ofstd/oferror.h ../include/dcmtk/ofstd/ofthread.h \
+ ../include/dcmtk/ofstd/ofexport.h ../include/dcmtk/ofstd/ofstdinc.h \
+ ../include/dcmtk/ofstd/ofstream.h ../include/dcmtk/ofstd/ofstring.h \
  ../include/dcmtk/ofstd/ofconsol.h
 oftime.o: oftime.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofstdinc.h ../include/dcmtk/ofstd/oftime.h \
@@ -204,9 +183,7 @@ oftime.o: oftime.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofexport.h ../include/dcmtk/ofstd/ofstream.h \
  ../include/dcmtk/ofstd/ofstd.h ../include/dcmtk/ofstd/oflist.h \
  ../include/dcmtk/ofstd/oftraits.h ../include/dcmtk/ofstd/ofcond.h \
- ../include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../include/dcmtk/ofstd/oferror.h
+ ../include/dcmtk/ofstd/oflimits.h ../include/dcmtk/ofstd/oferror.h
 oftimer.o: oftimer.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/oftimer.h ../include/dcmtk/ofstd/ofstream.h \
  ../include/dcmtk/ofstd/ofdefine.h ../include/dcmtk/ofstd/ofcast.h \
@@ -219,9 +196,7 @@ ofuuid.o: ofuuid.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofrand.h ../include/dcmtk/ofstd/ofthread.h \
  ../include/dcmtk/ofstd/ofstd.h ../include/dcmtk/ofstd/oflist.h \
  ../include/dcmtk/ofstd/oftraits.h ../include/dcmtk/ofstd/ofcond.h \
- ../include/dcmtk/ofstd/oflimits.h \
- ../../config/include/dcmtk/config/arith.h \
- ../include/dcmtk/ofstd/oferror.h
+ ../include/dcmtk/ofstd/oflimits.h ../include/dcmtk/ofstd/oferror.h
 ofxml.o: ofxml.cc ../../config/include/dcmtk/config/osconfig.h \
  ../include/dcmtk/ofstd/ofxml.h ../include/dcmtk/ofstd/ofstdinc.h \
  ../include/dcmtk/ofstd/ofdefine.h ../include/dcmtk/ofstd/ofcast.h \
index fb34332f14e43678571d5c958b29c08bdcea3a86..82584188e6545f71c85fb7e71e6f5f63bb3bbc3f 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2011-2016, OFFIS e.V.
+ *  Copyright (C) 2011-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -25,6 +25,7 @@
 
 #include "dcmtk/ofstd/offile.h"
 #include "dcmtk/ofstd/offilsys.h"
+#include "dcmtk/ofstd/ofutil.h"
 
 #ifdef HAVE_WINDOWS_H
 #include "dcmtk/ofstd/ofchrenc.h"   /* for class OFCharacterEncoding */
@@ -61,13 +62,14 @@ OFFilename::OFFilename(const OFString &filename,
     set(filename, convert);
 }
 
-OFFilename::OFFilename(const OFpath &path)
+OFFilename::OFFilename(const OFpath &path,
+                       const OFBool convert)
   : filename_(NULL)
 #if (defined(WIDE_CHAR_FILE_IO_FUNCTIONS) || defined(WIDE_CHAR_MAIN_FUNCTION)) && defined(_WIN32)
   , wfilename_(NULL)
 #endif
 {
-    set(path.native(), OFTrue);
+    set(path, convert);
 }
 
 #if (defined(WIDE_CHAR_FILE_IO_FUNCTIONS) || defined(WIDE_CHAR_MAIN_FUNCTION)) && defined(_WIN32)
@@ -130,13 +132,9 @@ void OFFilename::clear()
 
 void OFFilename::swap(OFFilename &arg)
 {
-    char *charPointer = filename_;
-    filename_ = arg.filename_;
-    arg.filename_ = charPointer;
+    OFswap(filename_, arg.filename_);
 #if (defined(WIDE_CHAR_FILE_IO_FUNCTIONS) || defined(WIDE_CHAR_MAIN_FUNCTION)) && defined(_WIN32)
-    wchar_t *wideCharPointer = wfilename_;
-    wfilename_ = arg.wfilename_;
-    arg.wfilename_ = wideCharPointer;
+    OFswap(wfilename_, arg.wfilename_);
 #endif
 }
 
@@ -186,6 +184,13 @@ void OFFilename::set(const OFString &filename,
 }
 
 
+void OFFilename::set(const OFpath &path,
+                     const OFBool convert)
+{
+    set(path.native(), convert);
+}
+
+
 #if (defined(WIDE_CHAR_FILE_IO_FUNCTIONS) || defined(WIDE_CHAR_MAIN_FUNCTION)) && defined(_WIN32)
 void OFFilename::set(const wchar_t *filename,
                      const OFBool convert)
index 3986939a3ab477a16cd563abfe3ef471f12142a0..2ee83427aa3db76a56b9a6dc01bee5524a7f7021 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2001-2019, OFFIS e.V.
+ *  Copyright (C) 2001-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -471,7 +471,7 @@ OFBool OFStandard::fileExists(const OFFilename &fileName)
             fileAttr = GetFileAttributesW(fileName.getWideCharPointer());
         else
 #endif
-            fileAttr = GetFileAttributes(fileName.getCharPointer());
+            fileAttr = GetFileAttributesA(fileName.getCharPointer());
         if (fileAttr != 0xffffffff)
         {
             /* check file type (not a directory?) */
@@ -501,7 +501,7 @@ OFBool OFStandard::dirExists(const OFFilename &dirName)
             fileAttr = GetFileAttributesW(dirName.getWideCharPointer());
         else
 #endif
-            fileAttr = GetFileAttributes(dirName.getCharPointer());
+            fileAttr = GetFileAttributesA(dirName.getCharPointer());
         if (fileAttr != 0xffffffff)
         {
             /* check file type (is a directory?) */
@@ -1875,6 +1875,7 @@ double OFStandard::atof(const char *s, OFBool *success)
     int expSign = 0;
     double fraction;
     int exponent = 0; // Exponent read from "EX" field.
+    int old_exponent = 0;
     const char *pExp; // Temporarily holds location of exponent in string.
 
     /* Exponent that derives from the fractional part.  Under normal
@@ -2000,8 +2001,24 @@ double OFStandard::atof(const char *s, OFBool *success)
         }
         while (isdigit(OFstatic_cast(unsigned char, *p)))
         {
+            old_exponent = exponent;
             exponent = exponent * 10 + (*p - '0');
             ++p;
+            if (exponent < old_exponent)
+            {
+              // overflow of the exponent. We cannot represent this number in an integer
+              // and also not in a double, where the exponent must not be larger than 308.
+              if (expSign)
+              {
+                // negative exponent. return 0 and leave success flag set to false
+                return 0.0;
+              }
+              else
+              {
+                // positive exponent. return plus/minus HUGE_VAL, depending on the sign bit
+                if (sign) return -HUGE_VAL; else return HUGE_VAL;
+              }
+            }
         }
     }
 
index d537315d9af3a91f8b0575361c3ff51fe83adf18..1e8674a04ed3abbb6ce86a41920b77ef142c951c 100644 (file)
@@ -24,7 +24,7 @@
 ** A simple string class
 ** - for OFFIS projects when an ANSI string class is not always available
 ** - based on the ANSI-C++ specifications
-** - this impementation is intended to be slow but reliable
+** - this implementation is intended to be slow but reliable
 ** - it is known to be slow but is it reliable?
 */
 
@@ -527,7 +527,7 @@ OFString::find (const OFString& pattern, size_t pos) const
         return OFString_npos;
     }
     for (size_t i = pos; i < this_size; i++) {
-        /* is there enought space for the pattern? */
+        /* is there enough space for the pattern? */
         if ((i + pattern_size) > this_size) {
             return OFString_npos;
         }
index 9fd23db697d0ac752d520a3a57bddf3923c0c6c1..a3761f7c7d0faa6456e56ac4e2467233443ac645 100644 (file)
@@ -128,7 +128,7 @@ void OFTempFile::getTempPath(OFString& sPath)
 #ifdef _WIN32
 #define BUFFER_SIZE 1024
     char buffer[BUFFER_SIZE];
-    GetTempPath(BUFFER_SIZE, buffer);
+    GetTempPathA(BUFFER_SIZE, buffer);
     sPath = buffer;
 #elif defined(__ANDROID__)
     sPath = ANDROID_TEMPORARY_FILES_LOCATION;
index 75099d2b9efc1b50b9902a126bc0f5bcaebb756e..72941e1769dc91515b6a6d43476202b300c34695 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2002-2018, OFFIS e.V.
+ *  Copyright (C) 2002-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -191,8 +191,8 @@ OFBool OFTime::isTimeValid(const unsigned int hour,
                            const double second,
                            const double timeZone)
 {
-    /* check whether given time is valid */
-    return (hour < 24) && (minute < 60) && (second >= 0) && (second < 60) && (timeZone >= -12) && (timeZone <= 14);
+    /* check whether given time is valid (also support leap second) */
+    return (hour < 24) && (minute < 60) && (second >= 0) && (second <= 60) && (timeZone >= -12) && (timeZone <= 14);
 }
 
 
@@ -287,7 +287,7 @@ OFBool OFTime::setTimeInSeconds(const double seconds,
                                 const OFBool normalize)
 {
     OFBool status = OFFalse;
-    /* only change if the new time is valid */
+    /* only change if the new time is valid (leap second is not supported!) */
     if (normalize || ((seconds >= 0) && (seconds < 86400)))
     {
         /* first normalize the value first to the valid range of [0.0,86400.0[ */
index 5da97cd29a24720cc20c73453a00ec392d6ed976..b0cf04c7d1b1827b00791af51d0ac456d337c39c 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 1997-2014, OFFIS e.V.
+ *  Copyright (C) 1997-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -69,10 +69,9 @@ const ValuePair vp[] =
   // overflow is reported as infinity
   {"1.7976931348623157E+1000", HUGE_VAL, OFTrue},
 
-#if !defined(_MSC_VER) || _MSC_VER >= 1700
-  // underflow is reported as zero
-  {"2.2250738585072014E-1000", 0.0, OFTrue},
-#endif
+  // underflow should be reported as zero, but on some platforms that support
+  // denormalized floating point numbers this test case fails.
+  // {"2.2250738585072014E-1000", 0.0, OFTrue},
 
   {"NaN", OFnumeric_limits<double>::quiet_NaN(), OFTrue},
   {"INF", OFnumeric_limits<double>::infinity(), OFTrue},
index a419911bf296fb28315eb252c4d27eba570318f7..1cf9ef062b17badc6d7c6662b5ff6c99b1ed1a56 100644 (file)
@@ -23,6 +23,7 @@
 
 #define OFTEST_OFSTD_ONLY
 #include "dcmtk/ofstd/oftest.h"
+#include "dcmtk/ofstd/ofxml.h"
 
 OFTEST_REGISTER(ofstd_OFCharacterEncoding_1);
 OFTEST_REGISTER(ofstd_OFCharacterEncoding_2);
@@ -72,7 +73,9 @@ OFTEST_REGISTER(ofstd_testPaths_2);
 #ifdef WITH_THREADS
 OFTEST_REGISTER(ofstd_thread);
 #endif // WITH_THREADS
+#ifndef _XMLWIDECHAR
 OFTEST_REGISTER(ofstd_xmlParser);
+#endif
 OFTEST_REGISTER(ofstd_memory);
 OFTEST_REGISTER(ofstd_optional);
 OFTEST_REGISTER(ofstd_tuple);
index f02160857c10cdf9ac194c6fbdba8c88e59acb5d..150ae65be17482f05f7eab094ed92e26941a9a39 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2009-2011, OFFIS e.V.
+ *  Copyright (C) 2009-2019, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -71,4 +71,18 @@ OFTEST(ofstd_OFMap)
 
     OFCHECK_EQUAL(m.size(), 2);
     OFCHECK_EQUAL(m[3], 3);
+
+    // Check whether map is sorted
+    m.clear();
+    // Insert values in reverse order
+    for (i = 0; i < 6 ; ++i)
+        m[6 - i] = 6 - i;
+    // Check all elements are stored in sorted order
+    OFCHECK_EQUAL(m.size(), 6);
+    it = m.begin();
+    for (i = 1; i <= 6; ++i)
+    {
+        OFCHECK((*it).second == i);
+        it++;
+    }
 }
index f18250cc18ad37a226a8a066b2a90074477c53fe..4ea801eed4eead0d74d81de7d9875bdcec9b60ab 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2002-2017, OFFIS e.V.
+ *  Copyright (C) 2002-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
@@ -97,6 +97,10 @@ OFTEST(ofstd_OFTime)
     OFCHECK_EQUAL(time1.getTimeZone(), -9.75);
     OFCHECK(time1.setISOFormattedTime("12:15:30 +09:15"));
     OFCHECK_EQUAL(time1.getTimeZone(), +9.25);
+    /* check support for leap second */
+    OFCHECK(time1.setTime(23, 59, 59));
+    OFCHECK(time1.setTime(23, 59, 60));
+    OFCHECK(!time1.setTime(23, 59, 61));
     /* the "seconds" part is mandatory if time zone is present */
     OFCHECK(!time2.setISOFormattedTime("10:15 -02:30"));
     OFCHECK(!time2.setISOFormattedTime("1015+0100"));
index cfa44e1c2e0aaf45637b208087cff65499d0e5f5..45082fd07e3d90ef222a8b73d01ee457d3287e46 100644 (file)
@@ -1,6 +1,6 @@
 /*
  *
- *  Copyright (C) 2011-2018, OFFIS e.V.
+ *  Copyright (C) 2011-2020, OFFIS e.V.
  *  All rights reserved.  See COPYRIGHT file for details.
  *
  *  This software and supporting documentation were developed by
       "</parent>"                                                       \
     "</root>"
 
+// we cannot run this test if the XML parser is configured for wide characters
+// because the OFTest classes and macros do not support wide strings.
+#ifndef _XMLWIDECHAR
+
 OFTEST(ofstd_xmlParser)
 {
     int i = 0;
@@ -78,3 +82,9 @@ OFTEST(ofstd_xmlParser)
     OFCHECK(rootNode.getChildNode("parent").getChildNode("child" ,2).isEmpty());
     OFCHECK(rootNode.getChildNode("element").isAttributeSet("attribute"));
 }
+
+#else
+
+int ofstd_txml_cc_dummy_to_keep_linker_from_moaning = 0;
+
+#endif
\ No newline at end of file